From d48975c948320d7983a928c4eeede93e8540c503 Mon Sep 17 00:00:00 2001 From: Tobias Koppers Date: Wed, 19 Sep 2018 13:05:22 +0200 Subject: [PATCH] use types from schema --- .eslintrc.js | 2 +- lib/AmdMainTemplatePlugin.js | 4 +-- lib/Compilation.js | 3 +- lib/Compiler.js | 18 ++++------ lib/DynamicEntryPlugin.js | 7 ++-- lib/EntryOptionPlugin.js | 3 +- lib/LibraryTemplatePlugin.js | 43 ++++++++++++++++++------ lib/UmdMainTemplatePlugin.js | 3 +- lib/WebpackOptionsApply.js | 20 +++++++++-- lib/web/JsonpExportMainTemplatePlugin.js | 3 ++ lib/webpack.js | 13 ++++++- 11 files changed, 85 insertions(+), 34 deletions(-) diff --git a/.eslintrc.js b/.eslintrc.js index 37b4be6f4..79cee6b11 100644 --- a/.eslintrc.js +++ b/.eslintrc.js @@ -23,7 +23,7 @@ module.exports = { yoda: "error", eqeqeq: "error", "global-require": "off", - "brace-style": "error", + "brace-style": "off", "eol-last": "error", "no-extra-bind": "warn", "no-process-exit": "warn", diff --git a/lib/AmdMainTemplatePlugin.js b/lib/AmdMainTemplatePlugin.js index ff715ec6c..2093edac6 100644 --- a/lib/AmdMainTemplatePlugin.js +++ b/lib/AmdMainTemplatePlugin.js @@ -12,10 +12,10 @@ const Template = require("./Template"); class AmdMainTemplatePlugin { /** - * @param {string} name the library name + * @param {string=} name the library name */ constructor(name) { - /** @type {string} */ + /** @type {string=} */ this.name = name; } diff --git a/lib/Compilation.js b/lib/Compilation.js index a420da696..ca14499c1 100644 --- a/lib/Compilation.js +++ b/lib/Compilation.js @@ -402,7 +402,8 @@ class Compilation extends Tapable { this.inputFileSystem = compiler.inputFileSystem; this.requestShortener = compiler.requestShortener; - const options = (this.options = compiler.options); + const options = compiler.options; + this.options = options; this.outputOptions = options && options.output; /** @type {boolean=} */ this.bail = options && options.bail; diff --git a/lib/Compiler.js b/lib/Compiler.js index bf7338fca..9b23e7269 100644 --- a/lib/Compiler.js +++ b/lib/Compiler.js @@ -27,6 +27,9 @@ const RequestShortener = require("./RequestShortener"); const { makePathsRelative } = require("./util/identifier"); const ConcurrentCompilationError = require("./ConcurrentCompilationError"); +/** @typedef {import("../declarations/WebpackOptions").Entry} Entry */ +/** @typedef {import("../declarations/WebpackOptions").WebpackOptions} WebpackOptions */ + /** * @typedef {Object} CompilationParams * @property {NormalModuleFactory} normalModuleFactory @@ -34,16 +37,6 @@ const ConcurrentCompilationError = require("./ConcurrentCompilationError"); * @property {Set} compilationDependencies */ -/** @typedef {string|string[]} EntryValues */ -/** @typedef {Record} EntryOptionValues */ - -/** - * @callback EntryOptionValuesFunction - * @returns {EntryOptionValues | EntryValues} the computed value - */ - -/** @typedef {EntryOptionValuesFunction | EntryOptionValues | EntryValues} EntryOptions */ - class Compiler extends Tapable { constructor(context) { super(); @@ -100,7 +93,7 @@ class Compiler extends Tapable { afterPlugins: new SyncHook(["compiler"]), /** @type {SyncHook} */ afterResolvers: new SyncHook(["compiler"]), - /** @type {SyncBailHook} */ + /** @type {SyncBailHook} */ entryOption: new SyncBailHook(["context", "entry"]) }; @@ -182,7 +175,8 @@ class Compiler extends Tapable { } }; - this.options = {}; + /** @type {WebpackOptions} */ + this.options = /** @type {WebpackOptions} */ ({}); this.context = context; diff --git a/lib/DynamicEntryPlugin.js b/lib/DynamicEntryPlugin.js index 99c1be2bf..be9b237b9 100644 --- a/lib/DynamicEntryPlugin.js +++ b/lib/DynamicEntryPlugin.js @@ -10,13 +10,14 @@ const MultiModuleFactory = require("./MultiModuleFactory"); const MultiEntryPlugin = require("./MultiEntryPlugin"); const SingleEntryPlugin = require("./SingleEntryPlugin"); +/** @typedef {import("../declarations/WebpackOptions").EntryDynamic} EntryDynamic */ +/** @typedef {import("../declarations/WebpackOptions").EntryStatic} EntryStatic */ /** @typedef {import("./Compiler")} Compiler */ -/** @typedef {import("./Compiler").EntryOptionValuesFunction} EntryOptionValuesFunction */ class DynamicEntryPlugin { /** * @param {string} context the context path - * @param {EntryOptionValuesFunction} entry the entry value + * @param {EntryDynamic} entry the entry value */ constructor(context, entry) { this.context = context; @@ -50,7 +51,7 @@ class DynamicEntryPlugin { /** * @param {string|string[]} entry entry value or array of entry values * @param {string} name name of entry - * @returns {Promise} returns the promise resolving the Compilation#addEntry function + * @returns {Promise} returns the promise resolving the Compilation#addEntry function */ const addEntry = (entry, name) => { const dep = DynamicEntryPlugin.createDependency(entry, name); diff --git a/lib/EntryOptionPlugin.js b/lib/EntryOptionPlugin.js index e992bc2c9..ddda157fe 100644 --- a/lib/EntryOptionPlugin.js +++ b/lib/EntryOptionPlugin.js @@ -8,11 +8,12 @@ const SingleEntryPlugin = require("./SingleEntryPlugin"); const MultiEntryPlugin = require("./MultiEntryPlugin"); const DynamicEntryPlugin = require("./DynamicEntryPlugin"); +/** @typedef {import("../declarations/WebpackOptions").EntryItem} EntryItem */ /** @typedef {import("./Compiler")} Compiler */ /** * @param {string} context context path - * @param {string | string[]} item entry array or single path + * @param {EntryItem} item entry array or single path * @param {string} name entry key name * @returns {SingleEntryPlugin | MultiEntryPlugin} returns either a single or multi entry plugin */ diff --git a/lib/LibraryTemplatePlugin.js b/lib/LibraryTemplatePlugin.js index c871994fa..fe4307916 100644 --- a/lib/LibraryTemplatePlugin.js +++ b/lib/LibraryTemplatePlugin.js @@ -6,6 +6,7 @@ const SetVarMainTemplatePlugin = require("./SetVarMainTemplatePlugin"); +/** @typedef {import("../declarations/WebpackOptions").LibraryCustomUmdObject} LibraryCustomUmdObject */ /** @typedef {import("./Compiler")} Compiler */ /** @@ -18,12 +19,17 @@ const accessorToObjectAccess = accessor => { /** * @param {string=} base the path prefix - * @param {string|string[]} accessor the accessor + * @param {string|string[]|LibraryCustomUmdObject} accessor the accessor + * @param {"amd" | "commonjs" | "root"} umdProperty property used when a custom umd object is provided * @param {string=} joinWith the element separator * @returns {string} the path */ -const accessorAccess = (base, accessor, joinWith = "; ") => { - const accessors = Array.isArray(accessor) ? accessor : [accessor]; +const accessorAccess = (base, accessor, umdProperty, joinWith = "; ") => { + const normalizedAccessor = + typeof accessor === "object" ? accessor[umdProperty] : accessor; + const accessors = Array.isArray(normalizedAccessor) + ? normalizedAccessor + : [normalizedAccessor]; return accessors .map((_, idx) => { const a = base @@ -40,7 +46,7 @@ const accessorAccess = (base, accessor, joinWith = "; ") => { class LibraryTemplatePlugin { /** - * @param {string} name name of library + * @param {string|string[]|LibraryCustomUmdObject} name name of library * @param {string} target type of library * @param {boolean} umdNamedDefine setting this to true will name the UMD module * @param {string|TODO} auxiliaryComment comment in the UMD wrapper @@ -68,14 +74,22 @@ class LibraryTemplatePlugin { } switch (this.target) { case "var": + if ( + !this.name || + (typeof this.name === "object" && !Array.isArray(this.name)) + ) { + throw new Error( + "library name must be set and not an UMD custom object for non-UMD target" + ); + } new SetVarMainTemplatePlugin( - `var ${accessorAccess(undefined, this.name)}`, + `var ${accessorAccess(undefined, this.name, "root")}`, false ).apply(compilation); break; case "assign": new SetVarMainTemplatePlugin( - accessorAccess(undefined, this.name), + accessorAccess(undefined, this.name, "root"), false ).apply(compilation); break; @@ -84,7 +98,7 @@ class LibraryTemplatePlugin { case "window": if (this.name) { new SetVarMainTemplatePlugin( - accessorAccess(this.target, this.name), + accessorAccess(this.target, this.name, "root"), false ).apply(compilation); } else { @@ -96,7 +110,8 @@ class LibraryTemplatePlugin { new SetVarMainTemplatePlugin( accessorAccess( compilation.runtimeTemplate.outputOptions.globalObject, - this.name + this.name, + "root" ), false ).apply(compilation); @@ -110,7 +125,7 @@ class LibraryTemplatePlugin { case "commonjs": if (this.name) { new SetVarMainTemplatePlugin( - accessorAccess("exports", this.name), + accessorAccess("exports", this.name, "commonjs"), false ).apply(compilation); } else { @@ -125,7 +140,13 @@ class LibraryTemplatePlugin { break; case "amd": { const AmdMainTemplatePlugin = require("./AmdMainTemplatePlugin"); - new AmdMainTemplatePlugin(this.name).apply(compilation); + if (this.name) { + if (typeof this.name !== "string") + throw new Error("library name must be a string for amd target"); + new AmdMainTemplatePlugin(this.name).apply(compilation); + } else { + new AmdMainTemplatePlugin().apply(compilation); + } break; } case "umd": @@ -140,6 +161,8 @@ class LibraryTemplatePlugin { } case "jsonp": { const JsonpExportMainTemplatePlugin = require("./web/JsonpExportMainTemplatePlugin"); + if (typeof this.name !== "string") + throw new Error("library name must be a string for jsonp target"); new JsonpExportMainTemplatePlugin(this.name).apply(compilation); break; } diff --git a/lib/UmdMainTemplatePlugin.js b/lib/UmdMainTemplatePlugin.js index 551ac76f8..ba5d24a2b 100644 --- a/lib/UmdMainTemplatePlugin.js +++ b/lib/UmdMainTemplatePlugin.js @@ -7,6 +7,7 @@ const { ConcatSource, OriginalSource } = require("webpack-sources"); const Template = require("./Template"); +/** @typedef {import("../declarations/WebpackOptions").LibraryCustomUmdObject} LibraryCustomUmdObject */ /** @typedef {import("./Compilation")} Compilation */ /** @@ -38,7 +39,7 @@ const accessorAccess = (base, accessor, joinWith = ", ") => { .join(joinWith); }; -/** @typedef {string | string[] | Record} UmdMainTemplatePluginName */ +/** @typedef {string | string[] | LibraryCustomUmdObject} UmdMainTemplatePluginName */ /** * @typedef {Object} AuxiliaryCommentObject diff --git a/lib/WebpackOptionsApply.js b/lib/WebpackOptionsApply.js index 2456a7bd7..6593d492a 100644 --- a/lib/WebpackOptionsApply.js +++ b/lib/WebpackOptionsApply.js @@ -63,11 +63,19 @@ const DefinePlugin = require("./DefinePlugin"); const SizeLimitsPlugin = require("./performance/SizeLimitsPlugin"); const WasmFinalizeExportsPlugin = require("./wasm/WasmFinalizeExportsPlugin"); +/** @typedef {import("../declarations/WebpackOptions").WebpackOptions} WebpackOptions */ +/** @typedef {import("./Compiler")} Compiler */ + class WebpackOptionsApply extends OptionsApply { constructor() { super(); } + /** + * @param {WebpackOptions} options options object + * @param {Compiler} compiler compiler object + * @returns {WebpackOptions} options object + */ process(options, compiler) { let ExternalsPlugin; compiler.outputPath = options.output.path; @@ -75,6 +83,8 @@ class WebpackOptionsApply extends OptionsApply { compiler.recordsOutputPath = options.recordsOutputPath || options.recordsPath; compiler.name = options.name; + // TODO webpack 5 refactor this to MultiCompiler.setDependencies() with a WeakMap + // @ts-ignore TODO compiler.dependencies = options.dependencies; if (typeof options.target === "string") { let JsonpTemplatePlugin; @@ -201,7 +211,9 @@ class WebpackOptionsApply extends OptionsApply { default: throw new Error("Unsupported target '" + options.target + "'."); } - } else if (options.target !== false) { + } + // @ts-ignore This is always true, which is good this way + else if (options.target !== false) { options.target(compiler); } else { throw new Error("Unsupported target '" + options.target + "'."); @@ -450,7 +462,11 @@ class WebpackOptionsApply extends OptionsApply { } if (options.optimization.minimize) { for (const minimizer of options.optimization.minimizer) { - minimizer.apply(compiler); + if (typeof minimizer === "function") { + minimizer.apply(compiler); + } else { + minimizer.apply(compiler); + } } } diff --git a/lib/web/JsonpExportMainTemplatePlugin.js b/lib/web/JsonpExportMainTemplatePlugin.js index c29740493..064b249e3 100644 --- a/lib/web/JsonpExportMainTemplatePlugin.js +++ b/lib/web/JsonpExportMainTemplatePlugin.js @@ -7,6 +7,9 @@ const { ConcatSource } = require("webpack-sources"); class JsonpExportMainTemplatePlugin { + /** + * @param {string} name jsonp function name + */ constructor(name) { this.name = name; } diff --git a/lib/webpack.js b/lib/webpack.js index 61357818e..58c96d15b 100644 --- a/lib/webpack.js +++ b/lib/webpack.js @@ -15,6 +15,13 @@ const webpackOptionsSchema = require("../schemas/WebpackOptions.json"); const RemovedPluginError = require("./RemovedPluginError"); const version = require("../package.json").version; +/** @typedef {import("../declarations/WebpackOptions").WebpackOptions} WebpackOptions */ + +/** + * @param {WebpackOptions} options options object + * @param {function(Error=, Stats=): void=} callback callback + * @returns {Compiler | MultiCompiler} the compiler object + */ const webpack = (options, callback) => { const webpackOptionsValidationErrors = validateSchema( webpackOptionsSchema, @@ -34,7 +41,11 @@ const webpack = (options, callback) => { new NodeEnvironmentPlugin().apply(compiler); if (options.plugins && Array.isArray(options.plugins)) { for (const plugin of options.plugins) { - plugin.apply(compiler); + if (typeof plugin === "function") { + plugin.apply(compiler); + } else { + plugin.apply(compiler); + } } } compiler.hooks.environment.call();