WXL
3 天以前 9bce51f651aad297ef9eb6df832bfdaf1de05d84
node_modules/webpack/lib/util/comparators.js
@@ -5,6 +5,7 @@
"use strict";
const { getFullModuleName } = require("../ids/IdHelpers");
const { compareRuntime } = require("./runtime");
/** @typedef {import("../Chunk")} Chunk */
@@ -13,6 +14,7 @@
/** @typedef {import("../ChunkGraph")} ChunkGraph */
/** @typedef {import("../ChunkGraph").ModuleId} ModuleId */
/** @typedef {import("../ChunkGroup")} ChunkGroup */
/** @typedef {import("../Compiler")} Compiler */
/** @typedef {import("../Dependency").DependencyLocation} DependencyLocation */
/** @typedef {import("../Dependency")} Dependency */
/** @typedef {import("../dependencies/HarmonyImportSideEffectDependency")} HarmonyImportSideEffectDependency */
@@ -22,27 +24,32 @@
/** @typedef {import("../dependencies/ModuleDependency")} ModuleDependency */
/**
 * Defines the dependency source order type used by this module.
 * @typedef {object} DependencySourceOrder
 * @property {number} main the main source order
 * @property {number} sub the sub source order
 */
/**
 * Defines the comparator type used by this module.
 * @template T
 * @typedef {(a: T, b: T) => -1 | 0 | 1} Comparator
 */
/**
 * Defines the raw parameterized comparator type used by this module.
 * @template {object} TArg
 * @template T
 * @typedef {(tArg: TArg, a: T, b: T) => -1 | 0 | 1} RawParameterizedComparator
 */
/**
 * Defines the parameterized comparator type used by this module.
 * @template {object} TArg
 * @template T
 * @typedef {(tArg: TArg) => Comparator<T>} ParameterizedComparator
 */
/**
 * Creates a cached parameterized comparator.
 * @template {object} TArg
 * @template {object} T
 * @param {RawParameterizedComparator<TArg, T>} fn comparator with argument
@@ -55,9 +62,10 @@
      const cachedResult = map.get(/** @type {EXPECTED_OBJECT} */ (arg));
      if (cachedResult !== undefined) return cachedResult;
      /**
       * Returns compare result.
       * @param {T} a first item
       * @param {T} b second item
       * @returns {-1|0|1} compare result
       * @returns {-1 | 0 | 1} compare result
       */
      const result = fn.bind(null, arg);
      map.set(/** @type {EXPECTED_OBJECT} */ (arg), result);
@@ -66,6 +74,7 @@
};
/**
 * Compares the provided values and returns their ordering.
 * @param {string | number} a first id
 * @param {string | number} b second id
 * @returns {-1 | 0 | 1} compare result
@@ -80,6 +89,7 @@
};
/**
 * Compares iterables.
 * @template T
 * @param {Comparator<T>} elementComparator comparator for elements
 * @returns {Comparator<Iterable<T>>} comparator for iterables of elements
@@ -88,9 +98,10 @@
   const cacheEntry = compareIteratorsCache.get(elementComparator);
   if (cacheEntry !== undefined) return cacheEntry;
   /**
    * Returns compare result.
    * @param {Iterable<T>} a first value
    * @param {Iterable<T>} b second value
    * @returns {-1|0|1} compare result
    * @returns {-1 | 0 | 1} compare result
    */
   const result = (a, b) => {
      const aI = a[Symbol.iterator]();
@@ -115,7 +126,7 @@
 * Compare two locations
 * @param {DependencyLocation} a A location node
 * @param {DependencyLocation} b A location node
 * @returns {-1|0|1} sorting comparator value
 * @returns {-1 | 0 | 1} sorting comparator value
 */
const compareLocations = (a, b) => {
   const isObjectA = typeof a === "object" && a !== null;
@@ -175,10 +186,11 @@
};
/**
 * Compares modules by id.
 * @param {ChunkGraph} chunkGraph the chunk graph
 * @param {Module} a module
 * @param {Module} b module
 * @returns {-1|0|1} compare result
 * @returns {-1 | 0 | 1} compare result
 */
const compareModulesById = (chunkGraph, a, b) =>
   compareIds(
@@ -187,9 +199,10 @@
   );
/**
 * Compares the provided values and returns their ordering.
 * @param {number} a number
 * @param {number} b number
 * @returns {-1|0|1} compare result
 * @returns {-1 | 0 | 1} compare result
 */
const compareNumbers = (a, b) => {
   if (typeof a !== typeof b) {
@@ -201,9 +214,10 @@
};
/**
 * Compares strings numeric.
 * @param {string} a string
 * @param {string} b string
 * @returns {-1|0|1} compare result
 * @returns {-1 | 0 | 1} compare result
 */
const compareStringsNumeric = (a, b) => {
   const aLength = a.length;
@@ -272,10 +286,11 @@
};
/**
 * Compares modules by post order index or identifier.
 * @param {ModuleGraph} moduleGraph the module graph
 * @param {Module} a module
 * @param {Module} b module
 * @returns {-1|0|1} compare result
 * @returns {-1 | 0 | 1} compare result
 */
const compareModulesByPostOrderIndexOrIdentifier = (moduleGraph, a, b) => {
   const cmp = compareNumbers(
@@ -287,10 +302,11 @@
};
/**
 * Compares modules by pre order index or identifier.
 * @param {ModuleGraph} moduleGraph the module graph
 * @param {Module} a module
 * @param {Module} b module
 * @returns {-1|0|1} compare result
 * @returns {-1 | 0 | 1} compare result
 */
const compareModulesByPreOrderIndexOrIdentifier = (moduleGraph, a, b) => {
   const cmp = compareNumbers(
@@ -302,10 +318,11 @@
};
/**
 * Compares modules by id or identifier.
 * @param {ChunkGraph} chunkGraph the chunk graph
 * @param {Module} a module
 * @param {Module} b module
 * @returns {-1|0|1} compare result
 * @returns {-1 | 0 | 1} compare result
 */
const compareModulesByIdOrIdentifier = (chunkGraph, a, b) => {
   const cmp = compareIds(
@@ -317,6 +334,20 @@
};
/**
 * Compare modules by their full name. This differs from comparing by identifier in that the values have been normalized to be relative to the compiler context.
 * @param {{ context: string, root: object }} compiler the compiler, used for context and cache
 * @param {Module} a module
 * @param {Module} b module
 * @returns {-1 | 0 | 1} compare result
 */
const compareModulesByFullName = (compiler, a, b) => {
   const aName = getFullModuleName(a, compiler.context, compiler.root);
   const bName = getFullModuleName(b, compiler.context, compiler.root);
   return compareIds(aName, bName);
};
/**
 * Compares the provided values and returns their ordering.
 * @param {ChunkGraph} chunkGraph the chunk graph
 * @param {Chunk} a chunk
 * @param {Chunk} b chunk
@@ -325,9 +356,10 @@
const compareChunks = (chunkGraph, a, b) => chunkGraph.compareChunks(a, b);
/**
 * Compares the provided values and returns their ordering.
 * @param {string} a first string
 * @param {string} b second string
 * @returns {-1|0|1} compare result
 * @returns {-1 | 0 | 1} compare result
 */
const compareStrings = (a, b) => {
   if (a < b) return -1;
@@ -336,6 +368,7 @@
};
/**
 * Compares chunk groups by index.
 * @param {ChunkGroup} a first chunk group
 * @param {ChunkGroup} b second chunk group
 * @returns {-1 | 0 | 1} compare result
@@ -344,6 +377,7 @@
   /** @type {number} */ (a.index) < /** @type {number} */ (b.index) ? -1 : 1;
/**
 * Represents TwoKeyWeakMap.
 * @template {EXPECTED_OBJECT} K1
 * @template {EXPECTED_OBJECT} K2
 * @template T
@@ -358,6 +392,7 @@
   }
   /**
    * Returns value.
    * @param {K1} key1 first key
    * @param {K2} key2 second key
    * @returns {T | undefined} value
@@ -371,6 +406,7 @@
   }
   /**
    * Updates value using the provided key1.
    * @param {K1} key1 first key
    * @param {K2} key2 second key
    * @param {T | undefined} value new value
@@ -390,6 +426,7 @@
const concatComparatorsCache = new TwoKeyWeakMap();
/**
 * Concat comparators.
 * @template T
 * @param {Comparator<T>} c1 comparator
 * @param {Comparator<T>} c2 comparator
@@ -406,9 +443,10 @@
   );
   if (cacheEntry !== undefined) return cacheEntry;
   /**
    * Returns compare result.
    * @param {T} a first value
    * @param {T} b second value
    * @returns {-1|0|1} compare result
    * @returns {-1 | 0 | 1} compare result
    */
   const result = (a, b) => {
      const res = c1(a, b);
@@ -420,6 +458,7 @@
};
/**
 * Defines the selector type used by this module.
 * @template A, B
 * @typedef {(input: A) => B | undefined | null} Selector
 */
@@ -428,6 +467,7 @@
const compareSelectCache = new TwoKeyWeakMap();
/**
 * Compares the provided values and returns their ordering.
 * @template T
 * @template R
 * @param {Selector<T, R>} getter getter for value
@@ -438,9 +478,10 @@
   const cacheEntry = compareSelectCache.get(getter, comparator);
   if (cacheEntry !== undefined) return cacheEntry;
   /**
    * Returns compare result.
    * @param {T} a first value
    * @param {T} b second value
    * @returns {-1|0|1} compare result
    * @returns {-1 | 0 | 1} compare result
    */
   const result = (a, b) => {
      const aValue = getter(a);
@@ -466,6 +507,7 @@
// TODO this is no longer needed when minimum node.js version is >= 12
// since these versions ship with a stable sort function
/**
 * Keep original order.
 * @template T
 * @param {Iterable<T>} iterable original ordered list
 * @returns {Comparator<T>} comparator
@@ -485,6 +527,7 @@
};
/**
 * Compares chunks natural.
 * @param {ChunkGraph} chunkGraph the chunk graph
 * @returns {Comparator<Chunk>} comparator
 */
@@ -496,6 +539,7 @@
      compareSelect((chunk) => chunk.runtime, compareRuntime),
      compareSelect(
         /**
          * Handles the callback logic for this hook.
          * @param {Chunk} chunk a chunk
          * @returns {Iterable<Module>} modules
          */
@@ -511,47 +555,42 @@
 * https://github.com/webpack/webpack/pull/19686
 * @param {Dependency[]} dependencies dependencies
 * @param {WeakMap<Dependency, DependencySourceOrder>} dependencySourceOrderMap dependency source order map
 * @param {((dep: Dependency, index: number) => void)=} onDependencyReSort optional callback to set index for each dependency
 * @returns {void}
 */
const sortWithSourceOrder = (dependencies, dependencySourceOrderMap) => {
   /**
    * @param {Dependency} dep dependency
    * @returns {number} source order
    */
   const getSourceOrder = (dep) => {
      if (dependencySourceOrderMap.has(dep)) {
         const { main } = /** @type {DependencySourceOrder} */ (
            dependencySourceOrderMap.get(dep)
         );
         return main;
      }
      return /** @type {number} */ (
         /** @type {ModuleDependency} */ (dep).sourceOrder
      );
   };
   /**
    * If the sourceOrder is a number, it means the dependency needs to be sorted.
    * @param {number | undefined} sourceOrder sourceOrder
    * @returns {boolean} needReSort
    */
   const needReSort = (sourceOrder) => {
      if (typeof sourceOrder === "number") {
         return true;
      }
      return false;
   };
   // Extract dependencies with sourceOrder and sort them
const sortWithSourceOrder = (
   dependencies,
   dependencySourceOrderMap,
   onDependencyReSort
) => {
   /** @type {{ dep: Dependency, main: number, sub: number }[]} */
   const withSourceOrder = [];
   /** @type {number[]} */
   const positions = [];
   // First pass: collect dependencies with sourceOrder
   for (let i = 0; i < dependencies.length; i++) {
      const dep = dependencies[i];
      const sourceOrder = getSourceOrder(dep);
      const cached = dependencySourceOrderMap.get(dep);
      if (needReSort(sourceOrder)) {
         withSourceOrder.push({ dep, sourceOrder, originalIndex: i });
      if (cached) {
         positions.push(i);
         withSourceOrder.push({
            dep,
            main: cached.main,
            sub: cached.sub
         });
      } else {
         const sourceOrder = /** @type {number | undefined} */ (
            /** @type {ModuleDependency} */ (dep).sourceOrder
         );
         if (typeof sourceOrder === "number") {
            positions.push(i);
            withSourceOrder.push({
               dep,
               main: sourceOrder,
               sub: 0
            });
         }
      }
   }
@@ -559,37 +598,19 @@
      return;
   }
   // Sort dependencies with sourceOrder
   withSourceOrder.sort((a, b) => {
      // Handle both dependencies in map case
      if (
         dependencySourceOrderMap.has(a.dep) &&
         dependencySourceOrderMap.has(b.dep)
      ) {
         const { main: mainA, sub: subA } = /** @type {DependencySourceOrder} */ (
            dependencySourceOrderMap.get(a.dep)
         );
         const { main: mainB, sub: subB } = /** @type {DependencySourceOrder} */ (
            dependencySourceOrderMap.get(b.dep)
         );
         if (mainA === mainB) {
            return compareNumbers(subA, subB);
         }
         return compareNumbers(mainA, mainB);
      if (a.main !== b.main) {
         return compareNumbers(a.main, b.main);
      }
      return compareNumbers(a.sourceOrder, b.sourceOrder);
      return compareNumbers(a.sub, b.sub);
   });
   // Second pass: build result array
   let sortedIndex = 0;
   for (let i = 0; i < dependencies.length; i++) {
      const dep = dependencies[i];
      const sourceOrder = getSourceOrder(dep);
      if (needReSort(sourceOrder)) {
         dependencies[i] = withSourceOrder[sortedIndex].dep;
         sortedIndex++;
   // Second pass: place sorted deps back to original positions
   for (let i = 0; i < positions.length; i++) {
      const depIndex = positions[i];
      dependencies[depIndex] = withSourceOrder[i].dep;
      if (onDependencyReSort) {
         onDependencyReSort(dependencies[depIndex], depIndex);
      }
   }
};
@@ -599,9 +620,10 @@
module.exports.compareChunks =
   createCachedParameterizedComparator(compareChunks);
/**
 * Returns compare result.
 * @param {Chunk} a chunk
 * @param {Chunk} b chunk
 * @returns {-1|0|1} compare result
 * @returns {-1 | 0 | 1} compare result
 */
module.exports.compareChunksById = (a, b) =>
   compareIds(/** @type {ChunkId} */ (a.id), /** @type {ChunkId} */ (b.id));
@@ -613,6 +635,11 @@
module.exports.compareLocations = compareLocations;
/** @type {ParameterizedComparator<Compiler, Module>} */
module.exports.compareModulesByFullName = createCachedParameterizedComparator(
   compareModulesByFullName
);
/** @type {ParameterizedComparator<ChunkGraph, Module>} */
module.exports.compareModulesById =
   createCachedParameterizedComparator(compareModulesById);
@@ -620,9 +647,10 @@
module.exports.compareModulesByIdOrIdentifier =
   createCachedParameterizedComparator(compareModulesByIdOrIdentifier);
/**
 * Returns compare result.
 * @param {Module} a module
 * @param {Module} b module
 * @returns {-1|0|1} compare result
 * @returns {-1 | 0 | 1} compare result
 */
module.exports.compareModulesByIdentifier = (a, b) =>
   compareIds(a.identifier(), b.identifier());