Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
/node_modules
/coverage
/types

############
## Windows
Expand Down
1 change: 1 addition & 0 deletions .prettierignore
Original file line number Diff line number Diff line change
@@ -1,2 +1,3 @@
package.json
package-lock.json
types
25 changes: 23 additions & 2 deletions eslint.config.mjs
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ import config from "eslint-config-webpack";

export default defineConfig([
{
ignores: [".changeset/"]
ignores: [".changeset/", "types/"]
},
{
extends: [config],
Expand All @@ -19,6 +19,17 @@ export default defineConfig([
}
}
},
{
// README code samples use `Function` and `Array<...>` to mirror the
// public `tapable.d.ts` types. Disable the strict TypeScript rules
// for README — they only activate when `typescript` is a direct
// devDependency (added for type generation in `lib/`).
files: ["**/*.md/*"],
rules: {
"@typescript-eslint/no-unsafe-function-type": "off",
"@typescript-eslint/array-type": "off"
}
},
{
files: ["benchmark/**/*"],
languageOptions: {
Expand All @@ -32,7 +43,17 @@ export default defineConfig([
"n/hashbang": "off",
"n/no-unsupported-features/es-syntax": "off",
"n/no-unsupported-features/node-builtins": "off",
"n/no-process-exit": "off"
"n/no-process-exit": "off",
// Benchmark files predate strict JSDoc rules and use loose JSDoc.
// The strict rules only activate when `typescript` is a direct
// devDependency (added for type generation in `lib/`).
"jsdoc/require-jsdoc": "off",
"jsdoc/require-param-description": "off",
"jsdoc/require-returns-description": "off",
"jsdoc/no-restricted-syntax": "off",
"jsdoc/reject-function-type": "off",
"jsdoc/type-formatting": "off",
"jsdoc/tag-lines": "off"
}
}
]);
59 changes: 56 additions & 3 deletions lib/AsyncParallelBailHook.js
Original file line number Diff line number Diff line change
Expand Up @@ -7,10 +7,39 @@
const Hook = require("./Hook");
const HookCodeFactory = require("./HookCodeFactory");

/** @typedef {import("./Hook").EXPECTED_ANY} EXPECTED_ANY */
/** @typedef {import("./Hook").EXPECTED_FUNCTION} EXPECTED_FUNCTION */
/** @typedef {import("./Hook").UnsetAdditionalOptions} UnsetAdditionalOptions */
/** @typedef {import("./Hook").CompileOptions<EXPECTED_ANY, EXPECTED_ANY, EXPECTED_ANY>} CompileOptions */
/** @typedef {import("./HookCodeFactory").ContentOptions} ContentOptions */
/**
* @template {EXPECTED_ANY[]} T
* @typedef {import("./Hook").ArgumentNames<T>} ArgumentNames
*/
/**
* @template T
* @typedef {import("./Hook").AsArray<T>} AsArray
*/

/**
* Mirror of the `AsyncParallelBailHook` class declared in `tapable.d.ts` for
* use as the factory function's return type, so `new AsyncParallelBailHook(...)`
* resolves to the specific subclass type instead of the generic `Hook`.
* @template T
* @template R
* @template [AdditionalOptions=UnsetAdditionalOptions]
* @typedef {import("../tapable").AsyncParallelBailHook<T, R, AdditionalOptions>} AsyncParallelBailHookType
*/

class AsyncParallelBailHookCodeFactory extends HookCodeFactory {
/**
* @param {ContentOptions} options content generation options
* @returns {string} generated body code
*/
content({ onError, onResult, onDone }) {
const opts = /** @type {CompileOptions} */ (this.options);
let code = "";
code += `var _results = new Array(${this.options.taps.length});\n`;
code += `var _results = new Array(${opts.taps.length});\n`;
code += "var _checkDone = function() {\n";
code += "for(var i = 0; i < _results.length; i++) {\n";
code += "var item = _results[i];\n";
Expand Down Expand Up @@ -68,20 +97,44 @@ class AsyncParallelBailHookCodeFactory extends HookCodeFactory {

const factory = new AsyncParallelBailHookCodeFactory();

/**
* @template T
* @template R
* @template [AdditionalOptions=UnsetAdditionalOptions]
* @this {Hook<T, R, AdditionalOptions>}
* @param {CompileOptions} options compile options
* @returns {EXPECTED_FUNCTION} the compiled call function
*/
function COMPILE(options) {
factory.setup(this, options);
return factory.create(options);
}

function AsyncParallelBailHook(args = [], name = undefined) {
/**
* @constructor
* @template T
* @template R
* @template [AdditionalOptions=UnsetAdditionalOptions]
* @param {ArgumentNames<AsArray<T>>=} args argument names of the hook
* @param {string=} name name of the hook
* @returns {AsyncParallelBailHookType<T, R, AdditionalOptions>} a new AsyncParallelBailHook instance
*/
function AsyncParallelBailHook(
args = /** @type {ArgumentNames<AsArray<T>>} */ (/** @type {unknown} */ ([])),
name = undefined
) {
const hook = new Hook(args, name);
hook.constructor = AsyncParallelBailHook;
hook.compile = COMPILE;
// @ts-expect-error for performance reasons
hook._call = undefined;
hook.call = undefined;
return hook;
return /** @type {AsyncParallelBailHookType<T, R, AdditionalOptions>} */ (
/** @type {unknown} */ (hook)
);
}

/** @type {EXPECTED_ANY} */
AsyncParallelBailHook.prototype = null;

module.exports = AsyncParallelBailHook;
51 changes: 49 additions & 2 deletions lib/AsyncParallelHook.js
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,34 @@
const Hook = require("./Hook");
const HookCodeFactory = require("./HookCodeFactory");

/** @typedef {import("./Hook").EXPECTED_ANY} EXPECTED_ANY */
/** @typedef {import("./Hook").EXPECTED_FUNCTION} EXPECTED_FUNCTION */
/** @typedef {import("./Hook").CompileOptions<EXPECTED_ANY, EXPECTED_ANY, EXPECTED_ANY>} CompileOptions */
/** @typedef {import("./Hook").UnsetAdditionalOptions} UnsetAdditionalOptions */
/** @typedef {import("./HookCodeFactory").ContentOptions} ContentOptions */
/**
* @template {EXPECTED_ANY[]} T
* @typedef {import("./Hook").ArgumentNames<T>} ArgumentNames
*/
/**
* @template T
* @typedef {import("./Hook").AsArray<T>} AsArray
*/

/**
* Mirror of the `AsyncParallelHook` class declared in `tapable.d.ts` for use
* as the factory function's return type, so `new AsyncParallelHook(...)`
* resolves to the specific subclass type instead of the generic `Hook`.
* @template T
* @template [AdditionalOptions=UnsetAdditionalOptions]
* @typedef {import("../tapable").AsyncParallelHook<T, AdditionalOptions>} AsyncParallelHookType
*/

class AsyncParallelHookCodeFactory extends HookCodeFactory {
/**
* @param {ContentOptions} options content generation options
* @returns {string} generated body code
*/
content({ onError, onDone }) {
return this.callTapsParallel({
onError: (i, err, done, doneBreak) => onError(err) + doneBreak(true),
Expand All @@ -18,20 +45,40 @@ class AsyncParallelHookCodeFactory extends HookCodeFactory {

const factory = new AsyncParallelHookCodeFactory();

/**
* @this {Hook<EXPECTED_ANY, EXPECTED_ANY, EXPECTED_ANY>}
* @param {CompileOptions} options compile options
* @returns {EXPECTED_FUNCTION} the compiled call function
*/
function COMPILE(options) {
factory.setup(this, options);
return factory.create(options);
}

function AsyncParallelHook(args = [], name = undefined) {
/**
* @constructor
* @template T
* @template [AdditionalOptions=UnsetAdditionalOptions]
* @param {ArgumentNames<AsArray<T>>=} args argument names of the hook
* @param {string=} name name of the hook
* @returns {AsyncParallelHookType<T, AdditionalOptions>} a new AsyncParallelHook instance
*/
function AsyncParallelHook(
args = /** @type {ArgumentNames<AsArray<T>>} */ (/** @type {unknown} */ ([])),
name = undefined
) {
const hook = new Hook(args, name);
hook.constructor = AsyncParallelHook;
hook.compile = COMPILE;
// @ts-expect-error for performance reasons
hook._call = undefined;
hook.call = undefined;
return hook;
return /** @type {AsyncParallelHookType<T, AdditionalOptions>} */ (
/** @type {unknown} */ (hook)
);
}

/** @type {EXPECTED_ANY} */
AsyncParallelHook.prototype = null;

module.exports = AsyncParallelHook;
53 changes: 51 additions & 2 deletions lib/AsyncSeriesBailHook.js
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,35 @@
const Hook = require("./Hook");
const HookCodeFactory = require("./HookCodeFactory");

/** @typedef {import("./Hook").EXPECTED_ANY} EXPECTED_ANY */
/** @typedef {import("./Hook").EXPECTED_FUNCTION} EXPECTED_FUNCTION */
/** @typedef {import("./Hook").CompileOptions<EXPECTED_ANY, EXPECTED_ANY, EXPECTED_ANY>} CompileOptions */
/** @typedef {import("./Hook").UnsetAdditionalOptions} UnsetAdditionalOptions */
/** @typedef {import("./HookCodeFactory").ContentOptions} ContentOptions */
/**
* @template {EXPECTED_ANY[]} T
* @typedef {import("./Hook").ArgumentNames<T>} ArgumentNames
*/
/**
* @template T
* @typedef {import("./Hook").AsArray<T>} AsArray
*/

/**
* Mirror of the `AsyncSeriesBailHook` class declared in `tapable.d.ts` for
* use as the factory function's return type, so `new AsyncSeriesBailHook(...)`
* resolves to the specific subclass type instead of the generic `Hook`.
* @template T
* @template R
* @template [AdditionalOptions=UnsetAdditionalOptions]
* @typedef {import("../tapable").AsyncSeriesBailHook<T, R, AdditionalOptions>} AsyncSeriesBailHookType
*/

class AsyncSeriesBailHookCodeFactory extends HookCodeFactory {
/**
* @param {ContentOptions} options content generation options
* @returns {string} generated body code
*/
content({ onError, onResult, resultReturns, onDone }) {
return this.callTapsSeries({
onError: (i, err, next, doneBreak) => onError(err) + doneBreak(true),
Expand All @@ -23,20 +51,41 @@ class AsyncSeriesBailHookCodeFactory extends HookCodeFactory {

const factory = new AsyncSeriesBailHookCodeFactory();

/**
* @this {Hook<EXPECTED_ANY, EXPECTED_ANY, EXPECTED_ANY>}
* @param {CompileOptions} options compile options
* @returns {EXPECTED_FUNCTION} the compiled call function
*/
function COMPILE(options) {
factory.setup(this, options);
return factory.create(options);
}

function AsyncSeriesBailHook(args = [], name = undefined) {
/**
* @constructor
* @template T
* @template R
* @template [AdditionalOptions=UnsetAdditionalOptions]
* @param {ArgumentNames<AsArray<T>>=} args argument names of the hook
* @param {string=} name name of the hook
* @returns {AsyncSeriesBailHookType<T, R, AdditionalOptions>} a new AsyncSeriesBailHook instance
*/
function AsyncSeriesBailHook(
args = /** @type {ArgumentNames<AsArray<T>>} */ (/** @type {unknown} */ ([])),
name = undefined
) {
const hook = new Hook(args, name);
hook.constructor = AsyncSeriesBailHook;
hook.compile = COMPILE;
// @ts-expect-error for performance reasons
hook._call = undefined;
hook.call = undefined;
return hook;
return /** @type {AsyncSeriesBailHookType<T, R, AdditionalOptions>} */ (
/** @type {unknown} */ (hook)
);
}

/** @type {EXPECTED_ANY} */
AsyncSeriesBailHook.prototype = null;

module.exports = AsyncSeriesBailHook;
51 changes: 49 additions & 2 deletions lib/AsyncSeriesHook.js
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,34 @@
const Hook = require("./Hook");
const HookCodeFactory = require("./HookCodeFactory");

/** @typedef {import("./Hook").EXPECTED_ANY} EXPECTED_ANY */
/** @typedef {import("./Hook").EXPECTED_FUNCTION} EXPECTED_FUNCTION */
/** @typedef {import("./Hook").CompileOptions<EXPECTED_ANY, EXPECTED_ANY, EXPECTED_ANY>} CompileOptions */
/** @typedef {import("./Hook").UnsetAdditionalOptions} UnsetAdditionalOptions */
/** @typedef {import("./HookCodeFactory").ContentOptions} ContentOptions */
/**
* @template {EXPECTED_ANY[]} T
* @typedef {import("./Hook").ArgumentNames<T>} ArgumentNames
*/
/**
* @template T
* @typedef {import("./Hook").AsArray<T>} AsArray
*/

/**
* Mirror of the `AsyncSeriesHook` class declared in `tapable.d.ts` for use
* as the factory function's return type, so `new AsyncSeriesHook(...)`
* resolves to the specific subclass type instead of the generic `Hook`.
* @template T
* @template [AdditionalOptions=UnsetAdditionalOptions]
* @typedef {import("../tapable").AsyncSeriesHook<T, AdditionalOptions>} AsyncSeriesHookType
*/

class AsyncSeriesHookCodeFactory extends HookCodeFactory {
/**
* @param {ContentOptions} options content generation options
* @returns {string} generated body code
*/
content({ onError, onDone }) {
return this.callTapsSeries({
onError: (i, err, next, doneBreak) => onError(err) + doneBreak(true),
Expand All @@ -18,20 +45,40 @@ class AsyncSeriesHookCodeFactory extends HookCodeFactory {

const factory = new AsyncSeriesHookCodeFactory();

/**
* @this {Hook<EXPECTED_ANY, EXPECTED_ANY, EXPECTED_ANY>}
* @param {CompileOptions} options compile options
* @returns {EXPECTED_FUNCTION} the compiled call function
*/
function COMPILE(options) {
factory.setup(this, options);
return factory.create(options);
}

function AsyncSeriesHook(args = [], name = undefined) {
/**
* @constructor
* @template T
* @template [AdditionalOptions=UnsetAdditionalOptions]
* @param {ArgumentNames<AsArray<T>>=} args argument names of the hook
* @param {string=} name name of the hook
* @returns {AsyncSeriesHookType<T, AdditionalOptions>} a new AsyncSeriesHook instance
*/
function AsyncSeriesHook(
args = /** @type {ArgumentNames<AsArray<T>>} */ (/** @type {unknown} */ ([])),
name = undefined
) {
const hook = new Hook(args, name);
hook.constructor = AsyncSeriesHook;
hook.compile = COMPILE;
// @ts-expect-error for performance reasons
hook._call = undefined;
hook.call = undefined;
return hook;
return /** @type {AsyncSeriesHookType<T, AdditionalOptions>} */ (
/** @type {unknown} */ (hook)
);
}

/** @type {EXPECTED_ANY} */
AsyncSeriesHook.prototype = null;

module.exports = AsyncSeriesHook;
Loading