Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

hoist regexp literals in SourceMapDerToolPlugin #15722

Merged
merged 2 commits into from Mar 13, 2023
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
38 changes: 31 additions & 7 deletions lib/SourceMapDevToolPlugin.js
Expand Up @@ -47,13 +47,32 @@ const validate = createSchemaValidation(
* @property {ItemCacheFacade} cacheItem cache item
*/

const METACHARACTERS_REGEXP = /[-[\]\\/{}()*+?.^$|]/g;
TheLarkInn marked this conversation as resolved.
Show resolved Hide resolved
const CONTENT_HASH_DETECT_REGEXP = /\[contenthash(:\w+)?\]/;
const CSS_AND_JS_MODULE_EXTENSIONS_REGEXP = /\.((c|m)?js|css)($|\?)/i;
const CSS_EXTENSION_DETECT_REGEXP = /\.css($|\?)/i;
const MAP_URL_COMMENT_REGEXP = /\[map\]/g;
const URL_COMMENT_REGEXP = /\[url\]/g;
const URL_FORMATTING_REGEXP = /^\n\/\/(.*)$/;

/**
* Reset's .lastIndex of stateful Regular Expressions
* For when `test` or `exec` is called on them
* @param {RegExp} regexp Stateful Regular Expression to be reset
* @returns {void}
*
*/
const resetRegexpState = regexp => {
regexp.lastIndex = -1;
};

/**
* Escapes regular expression metacharacters
* @param {string} str String to quote
* @returns {string} Escaped string
*/
const quoteMeta = str => {
return str.replace(/[-[\]\\/{}()*+?.^$|]/g, "\\$&");
return str.replace(METACHARACTERS_REGEXP, "\\$&");
};

/**
Expand Down Expand Up @@ -152,7 +171,7 @@ class SourceMapDevToolPlugin {
const fallbackModuleFilenameTemplate = this.fallbackModuleFilenameTemplate;
const requestShortener = compiler.requestShortener;
const options = this.options;
options.test = options.test || /\.((c|m)?js|css)($|\?)/i;
options.test = options.test || CSS_AND_JS_MODULE_EXTENSIONS_REGEXP;

const matchObject = ModuleFilenameHelpers.matchObject.bind(
undefined,
Expand Down Expand Up @@ -409,7 +428,9 @@ class SourceMapDevToolPlugin {
sourceMap.file = file;
const usesContentHash =
sourceMapFilename &&
/\[contenthash(:\w+)?\]/.test(sourceMapFilename);
CONTENT_HASH_DETECT_REGEXP.test(sourceMapFilename);

resetRegexpState(CONTENT_HASH_DETECT_REGEXP);

// If SourceMap and asset uses contenthash, avoid a circular dependency by hiding hash in `file`
if (usesContentHash && task.assetInfo.contenthash) {
Expand All @@ -428,13 +449,16 @@ class SourceMapDevToolPlugin {

/** @type {string | false} */
let currentSourceMappingURLComment = sourceMappingURLComment;
let cssExtensionDetected =
CSS_EXTENSION_DETECT_REGEXP.test(file);
resetRegexpState(CSS_EXTENSION_DETECT_REGEXP);
if (
currentSourceMappingURLComment !== false &&
/\.css($|\?)/i.test(file)
cssExtensionDetected
) {
currentSourceMappingURLComment =
currentSourceMappingURLComment.replace(
/^\n\/\/(.*)$/,
URL_FORMATTING_REGEXP,
"\n/*$1*/"
);
}
Expand Down Expand Up @@ -516,9 +540,9 @@ class SourceMapDevToolPlugin {
const asset = new ConcatSource(
new RawSource(source),
currentSourceMappingURLComment
.replace(/\[map\]/g, () => sourceMapString)
.replace(MAP_URL_COMMENT_REGEXP, () => sourceMapString)
.replace(
/\[url\]/g,
URL_COMMENT_REGEXP,
() =>
`data:application/json;charset=utf-8;base64,${Buffer.from(
sourceMapString,
Expand Down