test: refactor

This commit is contained in:
alexander-akait 2025-04-23 05:06:20 +03:00
parent 0414fd4f1c
commit af2acc56e8
18 changed files with 187 additions and 127 deletions

View File

@ -369,7 +369,8 @@ class FlagDependencyExportsPlugin {
(module, callback) => {
if (
typeof (
/** @type {BuildInfo} */ (module.buildInfo).hash
/** @type {BuildInfo} */
(module.buildInfo).hash
) !== "string"
) {
// not cacheable

View File

@ -35,7 +35,6 @@ const {
intersectRuntime
} = require("./util/runtime");
const ChunkRenderError = require("./ChunkRenderError");
const {
JAVASCRIPT_MODULE_TYPE_AUTO,
JAVASCRIPT_MODULE_TYPE_DYNAMIC,
@ -732,28 +731,15 @@ class HotModuleReplacementPlugin {
entry.pathOptions
));
}
let source;
try {
source = entry.render();
} catch (err) {
compilation.errors.push(
new ChunkRenderError(
hotUpdateChunk,
filename,
/** @type {Error} */ (err)
)
);
}
if (source) {
compilation.additionalChunkAssets.push(filename);
compilation.emitAsset(filename, source, {
hotModuleReplacement: true,
...assetInfo
});
if (currentChunk) {
currentChunk.files.add(filename);
compilation.hooks.chunkAsset.call(currentChunk, filename);
}
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 => {

View File

@ -28,6 +28,7 @@ const makeSerializable = require("./util/makeSerializable");
/** @typedef {import("./ConcatenationScope")} ConcatenationScope */
/** @typedef {import("./Dependency")} Dependency */
/** @typedef {import("./Dependency").UpdateHashContext} UpdateHashContext */
/** @typedef {import("./DependencyTemplate").CssData} CssData */
/** @typedef {import("./DependencyTemplates")} DependencyTemplates */
/** @typedef {import("./ExportsInfo").UsageStateType} UsageStateType */
/** @typedef {import("./FileSystemInfo")} FileSystemInfo */
@ -120,19 +121,25 @@ const makeSerializable = require("./util/makeSerializable");
* @typedef {object} KnownBuildInfo
* @property {boolean=} cacheable
* @property {boolean=} parsed
* @property {string=} moduleArgument
* @property {string=} exportsArgument
* @property {boolean=} strict
* @property {string=} moduleConcatenationBailout
* @property {LazySet<string>=} fileDependencies
* @property {LazySet<string>=} contextDependencies
* @property {LazySet<string>=} missingDependencies
* @property {LazySet<string>=} buildDependencies
* @property {ValueCacheVersions=} valueDependencies
* @property {TODO=} hash
* @property {Record<string, Source>=} assets
* @property {Map<string, AssetInfo | undefined>=} assetsInfo
* @property {(Snapshot | null)=} snapshot
* @property {string=} moduleArgument using in AMD
* @property {string=} exportsArgument using in AMD
* @property {string=} moduleConcatenationBailout using in CommonJs
* @property {boolean=} needCreateRequire using in APIPlugin
* @property {string=} resourceIntegrity using in HttpUriPlugin
* @property {LazySet<string>=} fileDependencies using in NormalModule
* @property {LazySet<string>=} contextDependencies using in NormalModule
* @property {LazySet<string>=} missingDependencies using in NormalModule
* @property {LazySet<string>=} buildDependencies using in NormalModule
* @property {ValueCacheVersions=} valueDependencies using in NormalModule
* @property {Record<string, Source>=} assets using in NormalModule
* @property {string=} hash using in NormalModule
* @property {(Snapshot | null)=} snapshot using in ContextModule
* @property {string=} fullContentHash for assets modules
* @property {string=} filename for assets modules
* @property {Map<string, AssetInfo | undefined>=} assetsInfo for assets modules
* @property {boolean=} dataUrl for assets modules
* @property {CssData=} cssData for css modules
*/
/** @typedef {Map<string, string | Set<string>>} ValueCacheVersions */

View File

@ -1632,7 +1632,11 @@ class NormalModule extends Module {
* @returns {void}
*/
updateHash(hash, context) {
hash.update(/** @type {BuildInfo} */ (this.buildInfo).hash);
const buildInfo = /** @type {BuildInfo} */ (this.buildInfo);
hash.update(
/** @type {string} */
(buildInfo.hash)
);
/** @type {Generator} */
(this.generator).updateHash(hash, {
module: this,

View File

@ -292,7 +292,7 @@ class CssGenerator extends Generator {
Array.from(exports).reduce((obj, [key, value]) => {
obj[key] = value;
return obj;
}, {})
}, /** @type {Record<string, string>} */ ({}))
);
return stringifiedExports.length + 42;

View File

@ -395,7 +395,7 @@ class CssModulesPlugin {
Array.from(exports).reduce((obj, [key, value]) => {
obj[key] = value;
return obj;
}, {})
}, /** @type {Record<string, string>} */ ({}))
)
);

View File

@ -550,9 +550,6 @@ module.exports = mergeExports(fn, {
css: {
get CssModulesPlugin() {
return require("./css/CssModulesPlugin");
},
get CssModule() {
return require("./CssModule");
}
},

View File

@ -0,0 +1,3 @@
module.exports = [
/Error in loader/,
];

View File

@ -0,0 +1,25 @@
import "./loader!./style.css";
it("should work", async function (done) {
const links = window.document.getElementsByTagName("link");
expect(links[0].sheet.css).toContain("color: red;");
NEXT(require("../../update")(done, {
ignoreErrored: true
}, () => {
expect(links[0].sheet.css).toContain("Error in loader");
NEXT(require("../../update")(done, {
ignoreErrored: true
}, () => {
expect(links[0].sheet.css).toContain("color: blue;");
done();
}));
}));
});
if (import.meta.webpackHot) {
import.meta.webpackHot.accept("./loader!./style.css");
}

View File

@ -0,0 +1,10 @@
module.exports = function(content) {
const callback = this.async();
if (content.includes("Failed")) {
callback(new Error("Error in loader"));
return;
}
callback(null, content);
};

View File

@ -0,0 +1,11 @@
.class {
color: red;
}
---
.class {
color: green;
}Failed
---
.class {
color: blue;
}

View File

@ -0,0 +1,6 @@
/** @type {import("../../../../").Configuration} */
module.exports = {
experiments: {
css: true
}
};

View File

@ -1,10 +0,0 @@
module.exports = [
[
// main.js render error
/Failed/
],
[
// main.hot-update.js render error
/Failed/
]
];

View File

@ -1,7 +0,0 @@
.html {
color: red;
}
---
html {
color: blue;
}Failed

View File

@ -1,12 +0,0 @@
import "./index.css";
it("should work", done => {
const links = window.document.getElementsByTagName("link");
expect(links[0].sheet.css).toContain("color: red;");
NEXT(
require("../../update")(done, true, () => {
const links = window.document.getElementsByTagName("link");
expect(links[0].sheet.css).toContain("color: blue;");
})
);
});

View File

@ -1,39 +0,0 @@
const webpack = require("../../../../");
/** @type {import("../../../../").Configuration} */
module.exports = {
entry: ["./index.js"],
experiments: {
css: true
},
plugins: [
{
apply(compiler) {
compiler.hooks.compilation.tap("Test", compilation => {
compilation.hooks.additionalTreeRuntimeRequirements.tap(
"Test",
(module, set, context) => {
// To prevent the runtime error `ReferenceError: __webpack_exports__ is not defined`,
// which occurs because the default `output.library` setting is `commonjs2`,
// resulting in adding `module.exports = __webpack_exports__;`.
set.add(webpack.RuntimeGlobals.startup);
set.add(webpack.RuntimeGlobals.exports);
}
);
webpack.javascript.JavascriptModulesPlugin.getCompilationHooks(
compilation
).renderModuleContent.tap("Test", (source, module) => {
if (module instanceof webpack.css.CssModule && module.hot) {
const s = module._source.source();
if (s.includes("Failed")) {
throw new Error("Failed");
}
}
return source;
});
});
}
}
]
};

112
types.d.ts vendored
View File

@ -906,12 +906,6 @@ declare abstract class ByTypeGenerator extends Generator {
) => null | Source;
}
declare const CIRCULAR_CONNECTION: unique symbol;
type CSSModuleCreateData = NormalModuleCreateData & {
cssLayer: CssLayer;
supports: Supports;
media: Media;
inheritance: [CssLayer, Supports, Media][];
};
declare class Cache {
constructor();
hooks: {
@ -3181,6 +3175,17 @@ declare interface CssAutoParserOptions {
*/
url?: boolean;
}
declare interface CssData {
/**
* whether export __esModule
*/
esModule: boolean;
/**
* the css exports
*/
exports: Map<string, string>;
}
/**
* Generator options for css modules.
@ -3284,16 +3289,11 @@ declare interface CssLoadingRuntimeModulePluginHooks {
linkPreload: SyncWaterfallHook<[string, Chunk]>;
linkPrefetch: SyncWaterfallHook<[string, Chunk]>;
}
declare class CssModule extends NormalModule {
constructor(options: CSSModuleCreateData);
declare abstract class CssModule extends NormalModule {
cssLayer: CssLayer;
supports: Supports;
media: Media;
inheritance: [CssLayer, Supports, Media][];
static deserialize(context: ObjectDeserializerContext): CssModule;
static getCompilationHooks(
compilation: Compilation
): NormalModuleCompilationHooks;
}
/**
@ -7725,19 +7725,97 @@ declare interface KnownAssetInfo {
declare interface KnownBuildInfo {
cacheable?: boolean;
parsed?: boolean;
moduleArgument?: string;
exportsArgument?: string;
strict?: boolean;
/**
* using in AMD
*/
moduleArgument?: string;
/**
* using in AMD
*/
exportsArgument?: string;
/**
* using in CommonJs
*/
moduleConcatenationBailout?: string;
/**
* using in APIPlugin
*/
needCreateRequire?: boolean;
/**
* using in HttpUriPlugin
*/
resourceIntegrity?: string;
/**
* using in NormalModule
*/
fileDependencies?: LazySet<string>;
/**
* using in NormalModule
*/
contextDependencies?: LazySet<string>;
/**
* using in NormalModule
*/
missingDependencies?: LazySet<string>;
/**
* using in NormalModule
*/
buildDependencies?: LazySet<string>;
/**
* using in NormalModule
*/
valueDependencies?: Map<string, string | Set<string>>;
hash?: any;
/**
* using in NormalModule
*/
assets?: Record<string, Source>;
assetsInfo?: Map<string, undefined | AssetInfo>;
/**
* using in NormalModule
*/
hash?: string;
/**
* using in ContextModule
*/
snapshot?: null | Snapshot;
/**
* for assets modules
*/
fullContentHash?: string;
/**
* for assets modules
*/
filename?: string;
/**
* for assets modules
*/
assetsInfo?: Map<string, undefined | AssetInfo>;
/**
* for assets modules
*/
dataUrl?: boolean;
/**
* for css modules
*/
cssData?: CssData;
}
declare interface KnownBuildMeta {
exportsType?: "namespace" | "dynamic" | "default" | "flagged";
@ -16561,7 +16639,7 @@ declare namespace exports {
export { AsyncWebAssemblyModulesPlugin, EnableWasmLoadingPlugin };
}
export namespace css {
export { CssModulesPlugin, CssModule };
export { CssModulesPlugin };
}
export namespace library {
export { AbstractLibraryPlugin, EnableLibraryPlugin };