123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123 |
- "use strict";
- /** @typedef {import("webpack").Compilation["inputFileSystem"] } InputFileSystem */
- /** @typedef {import("fs").Stats } Stats */
- /**
- * @param {InputFileSystem} inputFileSystem
- * @param {string} path
- * @return {Promise<undefined | Stats>}
- */
- function stat(inputFileSystem, path) {
- return new Promise((resolve, reject) => {
- inputFileSystem.stat(path,
- /**
- * @param {null | undefined | NodeJS.ErrnoException} err
- * @param {undefined | Stats} stats
- */
- // @ts-ignore
- (err, stats) => {
- if (err) {
- reject(err);
- return;
- }
- resolve(stats);
- });
- });
- }
- /**
- * @param {InputFileSystem} inputFileSystem
- * @param {string} path
- * @return {Promise<string | Buffer>}
- */
- function readFile(inputFileSystem, path) {
- return new Promise((resolve, reject) => {
- inputFileSystem.readFile(path,
- /**
- * @param {null | undefined | NodeJS.ErrnoException} err
- * @param {undefined | string | Buffer} data
- */
- (err, data) => {
- if (err) {
- reject(err);
- return;
- }
- resolve(
- /** @type {string | Buffer} */
- data);
- });
- });
- }
- const notSettled = Symbol(`not-settled`);
- /**
- * @template T
- * @typedef {() => Promise<T>} Task
- */
- /**
- * Run tasks with limited concurency.
- * @template T
- * @param {number} limit - Limit of tasks that run at once.
- * @param {Task<T>[]} tasks - List of tasks to run.
- * @returns {Promise<T[]>} A promise that fulfills to an array of the results
- */
- function throttleAll(limit, tasks) {
- if (!Number.isInteger(limit) || limit < 1) {
- throw new TypeError(`Expected \`limit\` to be a finite number > 0, got \`${limit}\` (${typeof limit})`);
- }
- if (!Array.isArray(tasks) || !tasks.every(task => typeof task === `function`)) {
- throw new TypeError(`Expected \`tasks\` to be a list of functions returning a promise`);
- }
- return new Promise((resolve, reject) => {
- const result = Array(tasks.length).fill(notSettled);
- const entries = tasks.entries();
- const next = () => {
- const {
- done,
- value
- } = entries.next();
- if (done) {
- const isLast = !result.includes(notSettled);
- if (isLast) {
- resolve(
- /** @type{T[]} **/
- result);
- }
- return;
- }
- const [index, task] = value;
- /**
- * @param {T} x
- */
- const onFulfilled = x => {
- result[index] = x;
- next();
- };
- task().then(onFulfilled, reject);
- };
- Array(limit).fill(0).forEach(next);
- });
- }
- module.exports = {
- stat,
- readFile,
- throttleAll
- };
|