css-loader 5.2.7 → 6.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/utils.js CHANGED
@@ -23,14 +23,14 @@ exports.isUrlRequestable = isUrlRequestable;
23
23
  exports.sort = sort;
24
24
  exports.combineRequests = combineRequests;
25
25
  exports.camelCase = camelCase;
26
+ exports.stringifyRequest = stringifyRequest;
27
+ exports.isDataUrl = isDataUrl;
26
28
  exports.WEBPACK_IGNORE_COMMENT_REGEXP = void 0;
27
29
 
28
30
  var _url = require("url");
29
31
 
30
32
  var _path = _interopRequireDefault(require("path"));
31
33
 
32
- var _loaderUtils = require("loader-utils");
33
-
34
34
  var _postcssModulesValues = _interopRequireDefault(require("postcss-modules-values"));
35
35
 
36
36
  var _postcssModulesLocalByDefault = _interopRequireDefault(require("postcss-modules-local-by-default"));
@@ -45,9 +45,78 @@ function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { de
45
45
  MIT License http://www.opensource.org/licenses/mit-license.php
46
46
  Author Tobias Koppers @sokra
47
47
  */
48
- const WEBPACK_IGNORE_COMMENT_REGEXP = /webpackIgnore:(\s+)?(true|false)/; // eslint-disable-next-line no-useless-escape
49
-
48
+ const WEBPACK_IGNORE_COMMENT_REGEXP = /webpackIgnore:(\s+)?(true|false)/;
50
49
  exports.WEBPACK_IGNORE_COMMENT_REGEXP = WEBPACK_IGNORE_COMMENT_REGEXP;
50
+ const matchRelativePath = /^\.\.?[/\\]/;
51
+
52
+ function isAbsolutePath(str) {
53
+ return _path.default.posix.isAbsolute(str) || _path.default.win32.isAbsolute(str);
54
+ }
55
+
56
+ function isRelativePath(str) {
57
+ return matchRelativePath.test(str);
58
+ }
59
+
60
+ function stringifyRequest(loaderContext, request) {
61
+ const splitted = request.split("!");
62
+ const {
63
+ context
64
+ } = loaderContext;
65
+ return JSON.stringify(splitted.map(part => {
66
+ // First, separate singlePath from query, because the query might contain paths again
67
+ const splittedPart = part.match(/^(.*?)(\?.*)/);
68
+ const query = splittedPart ? splittedPart[2] : "";
69
+ let singlePath = splittedPart ? splittedPart[1] : part;
70
+
71
+ if (isAbsolutePath(singlePath) && context) {
72
+ singlePath = _path.default.relative(context, singlePath);
73
+
74
+ if (isAbsolutePath(singlePath)) {
75
+ // If singlePath still matches an absolute path, singlePath was on a different drive than context.
76
+ // In this case, we leave the path platform-specific without replacing any separators.
77
+ // @see https://github.com/webpack/loader-utils/pull/14
78
+ return singlePath + query;
79
+ }
80
+
81
+ if (isRelativePath(singlePath) === false) {
82
+ // Ensure that the relative path starts at least with ./ otherwise it would be a request into the modules directory (like node_modules).
83
+ singlePath = `./${singlePath}`;
84
+ }
85
+ }
86
+
87
+ return singlePath.replace(/\\/g, "/") + query;
88
+ }).join("!"));
89
+ } // We can't use path.win32.isAbsolute because it also matches paths starting with a forward slash
90
+
91
+
92
+ const IS_NATIVE_WIN32_PATH = /^[a-z]:[/\\]|^\\\\/i;
93
+ const IS_MODULE_REQUEST = /^[^?]*~/;
94
+
95
+ function urlToRequest(url, root) {
96
+ let request;
97
+
98
+ if (IS_NATIVE_WIN32_PATH.test(url)) {
99
+ // absolute windows path, keep it
100
+ request = url;
101
+ } else if (typeof root !== "undefined" && /^\//.test(url)) {
102
+ request = root + url;
103
+ } else if (/^\.\.?\//.test(url)) {
104
+ // A relative url stays
105
+ request = url;
106
+ } else {
107
+ // every other url is threaded like a relative url
108
+ request = `./${url}`;
109
+ } // A `~` makes the url an module
110
+
111
+
112
+ if (IS_MODULE_REQUEST.test(request)) {
113
+ request = request.replace(IS_MODULE_REQUEST, "");
114
+ }
115
+
116
+ return request;
117
+ } // eslint-disable-next-line no-useless-escape
118
+
119
+
51
120
  const regexSingleEscape = /[ -,.\/:-@[\]\^`{-~]/;
52
121
  const regexExcessiveSpaces = /(^|\\+)?(\\[A-F0-9]{1,6})\x20(?![a-fA-F0-9\x20])/g;
53
122
 
@@ -253,8 +322,67 @@ function defaultGetLocalIdent(loaderContext, localIdentName, localName, options)
253
322
 
254
323
  const relativeResourcePath = normalizePath(_path.default.relative(options.context, loaderContext.resourcePath)); // eslint-disable-next-line no-param-reassign
255
324
 
256
- options.content = `${options.hashPrefix}${relativeMatchResource}${relativeResourcePath}\x00${localName}`;
257
- return (0, _loaderUtils.interpolateName)(loaderContext, localIdentName, options);
325
+ options.content = `${relativeMatchResource}${relativeResourcePath}\x00${localName}`;
326
+ let {
327
+ hashFunction,
328
+ hashDigest,
329
+ hashDigestLength
330
+ } = options;
331
+ const mathes = localIdentName.match(/\[(?:([^:\]]+):)?(?:(hash|contenthash|fullhash))(?::([a-z]+\d*))?(?::(\d+))?\]/i);
332
+
333
+ if (mathes) {
334
+ const hashName = mathes[2] || hashFunction;
335
+ hashFunction = mathes[1] || hashFunction;
336
+ hashDigest = mathes[3] || hashDigest;
337
+ hashDigestLength = mathes[4] || hashDigestLength; // `hash` and `contenthash` are same in `loader-utils` context
338
+ // let's keep `hash` for backward compatibility
339
+ // eslint-disable-next-line no-param-reassign
340
+
341
+ localIdentName = localIdentName.replace(/\[(?:([^:\]]+):)?(?:hash|contenthash|fullhash)(?::([a-z]+\d*))?(?::(\d+))?\]/gi, () => hashName === "fullhash" ? "[fullhash]" : "[contenthash]");
342
+ } // eslint-disable-next-line no-underscore-dangle
343
+
344
+
345
+ const hash = loaderContext._compiler.webpack.util.createHash(hashFunction);
346
+
347
+ const {
348
+ hashSalt
349
+ } = options;
350
+
351
+ if (hashSalt) {
352
+ hash.update(hashSalt);
353
+ }
354
+
355
+ hash.update(options.content);
356
+ const localIdentHash = hash.digest(hashDigest).slice(0, hashDigestLength).replace(/[/+]/g, "_").replace(/^\d/g, "_"); // TODO need improve on webpack side, we should allow to pass hash/contentHash without chunk property, also `data` for `getPath` should be looks good without chunk property
357
+
358
+ const ext = _path.default.extname(loaderContext.resourcePath);
359
+
360
+ const base = _path.default.basename(loaderContext.resourcePath);
361
+
362
+ const name = base.slice(0, base.length - ext.length);
363
+ const data = {
364
+ filename: _path.default.relative(options.context, loaderContext.resourcePath),
365
+ contentHash: localIdentHash,
366
+ chunk: {
367
+ name,
368
+ hash: localIdentHash,
369
+ contentHash: localIdentHash
370
+ }
371
+ }; // eslint-disable-next-line no-underscore-dangle
372
+
373
+ return loaderContext._compilation.getPath(localIdentName, data);
374
+ }
375
+
376
+ function fixedEncodeURIComponent(str) {
377
+ return str.replace(/[!'()*]/g, c => `%${c.charCodeAt(0).toString(16)}`);
378
+ }
379
+
380
+ function isDataUrl(url) {
381
+ if (/^data:/i.test(url)) {
382
+ return true;
383
+ }
384
+
385
+ return false;
258
386
  }
259
387
 
260
388
  const NATIVE_WIN32_PATH = /^[A-Z]:[/\\]|^\\\\/i;
@@ -277,6 +405,11 @@ function normalizeUrl(url, isStringValue) {
277
405
 
278
406
  normalizedUrl = unescape(normalizedUrl);
279
407
 
408
+ if (isDataUrl(url)) {
409
+ // Todo fixedEncodeURIComponent is workaround. Webpack resolver shouldn't handle "!" in dataURL
410
+ return fixedEncodeURIComponent(normalizedUrl);
411
+ }
412
+
280
413
  try {
281
414
  normalizedUrl = decodeURI(normalizedUrl);
282
415
  } catch (error) {// Ignore
@@ -285,12 +418,25 @@ function normalizeUrl(url, isStringValue) {
285
418
  return normalizedUrl;
286
419
  }
287
420
 
288
- function requestify(url, rootContext) {
289
- if (/^file:/i.test(url)) {
290
- return (0, _url.fileURLToPath)(url);
421
+ function requestify(url, rootContext, needToResolveURL = true) {
422
+ if (needToResolveURL) {
423
+ if (/^file:/i.test(url)) {
424
+ return (0, _url.fileURLToPath)(url);
425
+ }
426
+
427
+ return url.charAt(0) === "/" ? urlToRequest(url, rootContext) : urlToRequest(url);
428
+ }
429
+
430
+ if (url.charAt(0) === "/" || /^file:/i.test(url)) {
431
+ return url;
432
+ } // A `~` makes the url an module
433
+
434
+
435
+ if (IS_MODULE_REQUEST.test(url)) {
436
+ return url.replace(IS_MODULE_REQUEST, "");
291
437
  }
292
438
 
293
- return url.charAt(0) === "/" ? (0, _loaderUtils.urlToRequest)(url, rootContext) : (0, _loaderUtils.urlToRequest)(url);
439
+ return url;
294
440
  }
295
441
 
296
442
  function getFilter(filter, resourcePath) {
@@ -311,77 +457,86 @@ function getValidLocalName(localName, exportLocalsConvention) {
311
457
  return camelCase(localName);
312
458
  }
313
459
 
314
- const moduleRegExp = /\.module(s)?\.\w+$/i;
315
- const icssRegExp = /\.icss\.\w+$/i;
460
+ const IS_MODULES = /\.module(s)?\.\w+$/i;
461
+ const IS_ICSS = /\.icss\.\w+$/i;
316
462
 
317
463
  function getModulesOptions(rawOptions, loaderContext) {
464
+ if (typeof rawOptions.modules === "boolean" && rawOptions.modules === false) {
465
+ return false;
466
+ }
467
+
318
468
  const resourcePath = // eslint-disable-next-line no-underscore-dangle
319
469
  loaderContext._module && loaderContext._module.matchResource || loaderContext.resourcePath;
320
- let isIcss;
470
+ let auto;
471
+ let rawModulesOptions;
321
472
 
322
473
  if (typeof rawOptions.modules === "undefined") {
323
- const isModules = moduleRegExp.test(resourcePath);
324
-
325
- if (!isModules) {
326
- isIcss = icssRegExp.test(resourcePath);
327
- }
474
+ rawModulesOptions = {};
475
+ auto = true;
476
+ } else if (typeof rawOptions.modules === "boolean") {
477
+ rawModulesOptions = {};
478
+ } else if (typeof rawOptions.modules === "string") {
479
+ rawModulesOptions = {
480
+ mode: rawOptions.modules
481
+ };
482
+ } else {
483
+ rawModulesOptions = rawOptions.modules;
484
+ ({
485
+ auto
486
+ } = rawModulesOptions);
487
+ } // eslint-disable-next-line no-underscore-dangle
328
488
 
329
- if (!isModules && !isIcss) {
330
- return false;
331
- }
332
- } else if (typeof rawOptions.modules === "boolean" && rawOptions.modules === false) {
333
- return false;
334
- }
335
489
 
336
- let modulesOptions = {
337
- compileType: isIcss ? "icss" : "module",
338
- auto: true,
490
+ const {
491
+ outputOptions
492
+ } = loaderContext._compilation;
493
+ const modulesOptions = {
494
+ auto,
339
495
  mode: "local",
340
496
  exportGlobals: false,
341
497
  localIdentName: "[hash:base64]",
342
498
  localIdentContext: loaderContext.rootContext,
343
- localIdentHashPrefix: "",
499
+ localIdentHashSalt: outputOptions.hashSalt,
500
+ localIdentHashFunction: outputOptions.hashFunction,
501
+ localIdentHashDigest: outputOptions.hashDigest,
502
+ localIdentHashDigestLength: outputOptions.hashDigestLength,
344
503
  // eslint-disable-next-line no-undefined
345
504
  localIdentRegExp: undefined,
346
505
  // eslint-disable-next-line no-undefined
347
506
  getLocalIdent: undefined,
348
507
  namedExport: false,
349
- exportLocalsConvention: "asIs",
350
- exportOnlyLocals: false
508
+ exportLocalsConvention: rawModulesOptions.namedExport === true && typeof rawModulesOptions.exportLocalsConvention === "undefined" ? "camelCaseOnly" : "asIs",
509
+ exportOnlyLocals: false,
510
+ ...rawModulesOptions
351
511
  };
352
512
 
353
- if (typeof rawOptions.modules === "boolean" || typeof rawOptions.modules === "string") {
354
- modulesOptions.mode = typeof rawOptions.modules === "string" ? rawOptions.modules : "local";
355
- } else {
356
- if (rawOptions.modules) {
357
- if (typeof rawOptions.modules.auto === "boolean") {
358
- const isModules = rawOptions.modules.auto && moduleRegExp.test(resourcePath);
513
+ if (typeof modulesOptions.auto === "boolean") {
514
+ const isModules = modulesOptions.auto && IS_MODULES.test(resourcePath);
515
+ let isIcss;
359
516
 
360
- if (!isModules) {
361
- return false;
362
- }
363
- } else if (rawOptions.modules.auto instanceof RegExp) {
364
- const isModules = rawOptions.modules.auto.test(resourcePath);
365
-
366
- if (!isModules) {
367
- return false;
368
- }
369
- } else if (typeof rawOptions.modules.auto === "function") {
370
- const isModule = rawOptions.modules.auto(resourcePath);
517
+ if (!isModules) {
518
+ isIcss = IS_ICSS.test(resourcePath);
371
519
 
372
- if (!isModule) {
373
- return false;
374
- }
520
+ if (isIcss) {
521
+ modulesOptions.mode = "icss";
375
522
  }
523
+ }
376
524
 
377
- if (rawOptions.modules.namedExport === true && typeof rawOptions.modules.exportLocalsConvention === "undefined") {
378
- modulesOptions.exportLocalsConvention = "camelCaseOnly";
379
- }
525
+ if (!isModules && !isIcss) {
526
+ return false;
380
527
  }
528
+ } else if (modulesOptions.auto instanceof RegExp) {
529
+ const isModules = modulesOptions.auto.test(resourcePath);
381
530
 
382
- modulesOptions = { ...modulesOptions,
383
- ...(rawOptions.modules || {})
384
- };
531
+ if (!isModules) {
532
+ return false;
533
+ }
534
+ } else if (typeof modulesOptions.auto === "function") {
535
+ const isModule = modulesOptions.auto(resourcePath);
536
+
537
+ if (!isModule) {
538
+ return false;
539
+ }
385
540
  }
386
541
 
387
542
  if (typeof modulesOptions.mode === "function") {
@@ -398,10 +553,6 @@ function getModulesOptions(rawOptions, loaderContext) {
398
553
  }
399
554
  }
400
555
 
401
- if (/\[emoji(?::(\d+))?\]/i.test(modulesOptions.localIdentName)) {
402
- loaderContext.emitWarning("Emoji is deprecated and will be removed in next major release.");
403
- }
404
-
405
556
  return modulesOptions;
406
557
  }
407
558
 
@@ -442,11 +593,15 @@ function shouldUseURLPlugin(options) {
442
593
  }
443
594
 
444
595
  function shouldUseModulesPlugins(options) {
445
- return options.modules.compileType === "module";
596
+ if (typeof options.modules === "boolean" && options.modules === false) {
597
+ return false;
598
+ }
599
+
600
+ return options.modules.mode !== "icss";
446
601
  }
447
602
 
448
603
  function shouldUseIcssPlugin(options) {
449
- return options.icss === true || Boolean(options.modules);
604
+ return Boolean(options.modules);
450
605
  }
451
606
 
452
607
  function getModulesPlugins(options, loaderContext) {
@@ -455,7 +610,10 @@ function getModulesPlugins(options, loaderContext) {
455
610
  getLocalIdent,
456
611
  localIdentName,
457
612
  localIdentContext,
458
- localIdentHashPrefix,
613
+ localIdentHashSalt,
614
+ localIdentHashFunction,
615
+ localIdentHashDigest,
616
+ localIdentHashDigestLength,
459
617
  localIdentRegExp
460
618
  } = options.modules;
461
619
  let plugins = [];
@@ -470,7 +628,10 @@ function getModulesPlugins(options, loaderContext) {
470
628
  if (typeof getLocalIdent !== "undefined") {
471
629
  localIdent = getLocalIdent(loaderContext, localIdentName, unescape(exportName), {
472
630
  context: localIdentContext,
473
- hashPrefix: localIdentHashPrefix,
631
+ hashSalt: localIdentHashSalt,
632
+ hashFunction: localIdentHashFunction,
633
+ hashDigest: localIdentHashDigest,
634
+ hashDigestLength: localIdentHashDigestLength,
474
635
  regExp: localIdentRegExp
475
636
  });
476
637
  } // A null/undefined value signals that we should invoke the default
@@ -480,7 +641,10 @@ function getModulesPlugins(options, loaderContext) {
480
641
  if (typeof localIdent === "undefined" || localIdent === null) {
481
642
  localIdent = defaultGetLocalIdent(loaderContext, localIdentName, unescape(exportName), {
482
643
  context: localIdentContext,
483
- hashPrefix: localIdentHashPrefix,
644
+ hashSalt: localIdentHashSalt,
645
+ hashFunction: localIdentHashFunction,
646
+ hashDigest: localIdentHashDigest,
647
+ hashDigestLength: localIdentHashDigestLength,
484
648
  regExp: localIdentRegExp
485
649
  });
486
650
  return escapeLocalIdent(localIdent).replace(/\\\[local\\]/gi, exportName);
@@ -498,7 +662,6 @@ function getModulesPlugins(options, loaderContext) {
498
662
  return plugins;
499
663
  }
500
664
 
501
- const IS_NATIVE_WIN32_PATH = /^[a-z]:[/\\]|^\\\\/i;
502
665
  const ABSOLUTE_SCHEME = /^[a-z0-9+\-.]+:/i;
503
666
 
504
667
  function getURLType(source) {
@@ -582,14 +745,15 @@ function getImportCode(imports, options) {
582
745
  const {
583
746
  importName,
584
747
  url,
585
- icss
748
+ icss,
749
+ type
586
750
  } = item;
587
751
 
588
752
  if (options.esModule) {
589
753
  if (icss && options.modules.namedExport) {
590
754
  code += `import ${options.modules.exportOnlyLocals ? "" : `${importName}, `}* as ${importName}_NAMED___ from ${url};\n`;
591
755
  } else {
592
- code += `import ${importName} from ${url};\n`;
756
+ code += type === "url" ? `var ${importName} = new URL(${url}, import.meta.url);\n` : `import ${importName} from ${url};\n`;
593
757
  }
594
758
  } else {
595
759
  code += `var ${importName} = require(${url});\n`;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "css-loader",
3
- "version": "5.2.7",
3
+ "version": "6.0.0",
4
4
  "description": "css loader module for webpack",
5
5
  "license": "MIT",
6
6
  "repository": "webpack-contrib/css-loader",
@@ -13,7 +13,7 @@
13
13
  },
14
14
  "main": "dist/cjs.js",
15
15
  "engines": {
16
- "node": ">= 10.13.0"
16
+ "node": ">= 12.13.0"
17
17
  },
18
18
  "scripts": {
19
19
  "start": "npm run build -- -w",
@@ -39,56 +39,54 @@
39
39
  "dist"
40
40
  ],
41
41
  "peerDependencies": {
42
- "webpack": "^4.27.0 || ^5.0.0"
42
+ "webpack": "^5.0.0"
43
43
  },
44
44
  "dependencies": {
45
45
  "icss-utils": "^5.1.0",
46
- "loader-utils": "^2.0.0",
47
46
  "postcss": "^8.2.15",
48
47
  "postcss-modules-extract-imports": "^3.0.0",
49
48
  "postcss-modules-local-by-default": "^4.0.0",
50
49
  "postcss-modules-scope": "^3.0.0",
51
50
  "postcss-modules-values": "^4.0.0",
52
51
  "postcss-value-parser": "^4.1.0",
53
- "schema-utils": "^3.0.0",
54
52
  "semver": "^7.3.5"
55
53
  },
56
54
  "devDependencies": {
57
- "@babel/cli": "^7.14.3",
58
- "@babel/core": "^7.14.3",
59
- "@babel/preset-env": "^7.14.2",
55
+ "@babel/cli": "^7.14.5",
56
+ "@babel/core": "^7.14.6",
57
+ "@babel/preset-env": "^7.14.7",
60
58
  "@commitlint/cli": "^12.1.4",
61
59
  "@commitlint/config-conventional": "^12.1.4",
62
60
  "@webpack-contrib/eslint-config-webpack": "^3.0.0",
63
- "babel-jest": "^26.6.3",
61
+ "babel-jest": "^27.0.6",
64
62
  "cross-env": "^7.0.3",
65
63
  "del": "^6.0.0",
66
- "del-cli": "^3.0.1",
67
- "es-check": "^5.2.3",
68
- "eslint": "^7.26.0",
64
+ "del-cli": "^4.0.0",
65
+ "es-check": "^5.2.4",
66
+ "eslint": "^7.30.0",
69
67
  "eslint-config-prettier": "^8.3.0",
70
- "eslint-plugin-import": "^2.23.2",
68
+ "eslint-plugin-import": "^2.23.4",
71
69
  "file-loader": "^6.2.0",
72
- "husky": "^6.0.0",
73
- "jest": "^26.6.3",
70
+ "husky": "^7.0.1",
71
+ "jest": "^27.0.6",
74
72
  "less": "^4.1.1",
75
- "less-loader": "^7.1.0",
76
- "lint-staged": "^11.0.0",
73
+ "less-loader": "^10.0.1",
74
+ "lint-staged": "^11.0.1",
77
75
  "memfs": "^3.2.2",
78
- "mini-css-extract-plugin": "^1.6.0",
76
+ "mini-css-extract-plugin": "^2.1.0",
79
77
  "npm-run-all": "^4.1.5",
80
- "postcss-loader": "^4.3.0",
78
+ "postcss-loader": "^6.1.1",
81
79
  "postcss-preset-env": "^6.7.0",
82
- "prettier": "^2.3.0",
83
- "sass": "^1.32.13",
84
- "sass-loader": "^10.2.0",
85
- "standard-version": "^9.3.0",
80
+ "prettier": "^2.3.2",
81
+ "sass": "^1.35.2",
82
+ "sass-loader": "^12.1.0",
83
+ "standard-version": "^9.3.1",
86
84
  "strip-ansi": "^6.0.0",
87
- "style-loader": "^2.0.0",
85
+ "style-loader": "^3.1.0",
88
86
  "stylus": "^0.54.8",
89
- "stylus-loader": "^4.3.3",
87
+ "stylus-loader": "^6.1.0",
90
88
  "url-loader": "^4.1.1",
91
- "webpack": "^5.37.1"
89
+ "webpack": "^5.44.0"
92
90
  },
93
91
  "keywords": [
94
92
  "webpack",