css-loader 2.0.0 → 2.1.1

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/CHANGELOG.md CHANGED
@@ -2,6 +2,49 @@
2
2
 
3
3
  All notable changes to this project will be documented in this file. See [standard-version](https://github.com/conventional-changelog/standard-version) for commit guidelines.
4
4
 
5
+ <a name="2.1.1"></a>
6
+ ## [2.1.1](https://github.com/webpack-contrib/css-loader/compare/v2.1.0...v2.1.1) (2019-03-07)
7
+
8
+
9
+ ### Bug Fixes
10
+
11
+ * do not break selector with escaping ([#896](https://github.com/webpack-contrib/css-loader/issues/896)) ([0ba8c66](https://github.com/webpack-contrib/css-loader/commit/0ba8c66))
12
+ * source map generation when `sourceRoot` is present ([#901](https://github.com/webpack-contrib/css-loader/issues/901)) ([e9ce745](https://github.com/webpack-contrib/css-loader/commit/e9ce745))
13
+ * sourcemap generating when previous loader pass sourcemap as string ([#905](https://github.com/webpack-contrib/css-loader/issues/905)) ([3797e4d](https://github.com/webpack-contrib/css-loader/commit/3797e4d))
14
+
15
+
16
+
17
+ <a name="2.1.0"></a>
18
+ # [2.1.0](https://github.com/webpack-contrib/css-loader/compare/v2.0.2...v2.1.0) (2018-12-25)
19
+
20
+
21
+ ### Features
22
+
23
+ * support `image-set` without `url` ([#879](https://github.com/webpack-contrib/css-loader/issues/879)) ([21884e2](https://github.com/webpack-contrib/css-loader/commit/21884e2))
24
+
25
+
26
+
27
+ <a name="2.0.2"></a>
28
+ ## [2.0.2](https://github.com/webpack-contrib/css-loader/compare/v2.0.1...v2.0.2) (2018-12-21)
29
+
30
+
31
+ ### Bug Fixes
32
+
33
+ * inappropriate modification of animation keywords ([#876](https://github.com/webpack-contrib/css-loader/issues/876)) ([dfb2f8e](https://github.com/webpack-contrib/css-loader/commit/dfb2f8e))
34
+
35
+
36
+
37
+ <a name="2.0.1"></a>
38
+ # [2.0.1](https://github.com/webpack-contrib/css-loader/compare/v2.0.0...v2.0.1) (2018-12-14)
39
+
40
+
41
+ ### Bug Fixes
42
+
43
+ * safe checking if params are present for at rule ([#871](https://github.com/webpack-contrib/css-loader/issues/871)) ([a88fed1](https://github.com/webpack-contrib/css-loader/commit/a88fed1))
44
+ * `getLocalIdent` now accepts `false` value ([#865](https://github.com/webpack-contrib/css-loader/issues/865)) ([1825e8a](https://github.com/webpack-contrib/css-loader/commit/1825e8a))
45
+
46
+
47
+
5
48
  <a name="2.0.0"></a>
6
49
  # [2.0.0](https://github.com/webpack-contrib/css-loader/compare/v1.0.1...v2.0.0) (2018-12-07)
7
50
 
@@ -34,7 +77,7 @@ All notable changes to this project will be documented in this file. See [standa
34
77
 
35
78
  ### BREAKING CHANGES
36
79
 
37
- * resolving logic for `uls()` and `import` at-rules works the same everywhere, it does not matter whether css modules are enabled (with `global` and `local` module) or not. Examples - `url('image.png')` as `require('./image.png')`, `url('./image.png')` as `require('./image.png')`, `url('~module/image.png')` as `require('module/image.png')`.
80
+ * resolving logic for `url()` and `import` at-rules works the same everywhere, it does not matter whether css modules are enabled (with `global` and `local` module) or not. Examples - `url('image.png')` as `require('./image.png')`, `url('./image.png')` as `require('./image.png')`, `url('~module/image.png')` as `require('module/image.png')`.
38
81
  * by default css modules are disabled (now `modules: false` disable all css modules features), you can return old behaviour change this on `modules: 'global'`
39
82
  * `css-loader/locals` was dropped in favor `exportOnlyLocals` option
40
83
  * `import` option only affect on `import` at-rules and doesn't affect on `composes` declarations
package/README.md CHANGED
@@ -5,7 +5,6 @@
5
5
  <img width="200" height="200"
6
6
  src="https://webpack.js.org/assets/icon-square-big.svg">
7
7
  </a>
8
- <h1>CSS Loader</h1>
9
8
  </div>
10
9
 
11
10
  [![npm][npm]][npm-url]
@@ -20,10 +19,6 @@
20
19
 
21
20
  The `css-loader` interprets `@import` and `url()` like `import/require()` and will resolve them.
22
21
 
23
- ## Requirements
24
-
25
- This module requires a minimum of Node v6.9.0 and Webpack v4.0.0.
26
-
27
22
  ## Getting Started
28
23
 
29
24
  To begin, you'll need to install `css-loader`:
@@ -114,23 +109,26 @@ module.exports = {
114
109
 
115
110
  ## Options
116
111
 
117
- | Name | Type | Default | Description |
118
- | :-----------------------------------------: | :-------------------: | :-------------: | :------------------------------------------ |
119
- | **[`url`](#url)** | `{Boolean\|Function}` | `true` | Enable/Disable `url()` handling |
120
- | **[`import`](#import)** | `{Boolean\/Function}` | `true` | Enable/Disable @import handling |
121
- | **[`modules`](#modules)** | `{Boolean\|String}` | `false` | Enable/Disable CSS Modules and setup mode |
122
- | **[`localIdentName`](#localidentname)** | `{String}` | `[hash:base64]` | Configure the generated ident |
123
- | **[`sourceMap`](#sourcemap)** | `{Boolean}` | `false` | Enable/Disable Sourcemaps |
124
- | **[`camelCase`](#camelcase)** | `{Boolean\|String}` | `false` | Export Classnames in CamelCase |
125
- | **[`importLoaders`](#importloaders)** | `{Number}` | `0` | Number of loaders applied before CSS loader |
126
- | **[`exportOnlyLocals`](#exportonlylocals)** | `{Boolean}` | `false` | Export only locals |
112
+ | Name | Type | Default | Description |
113
+ | :-----------------------------------------: | :-------------------: | :-------------: | :----------------------------------------------------------------------- |
114
+ | **[`url`](#url)** | `{Boolean\|Function}` | `true` | Enable/Disable `url()` handling |
115
+ | **[`import`](#import)** | `{Boolean\/Function}` | `true` | Enable/Disable @import handling |
116
+ | **[`modules`](#modules)** | `{Boolean\|String}` | `false` | Enable/Disable CSS Modules and setup mode |
117
+ | **[`localIdentName`](#localidentname)** | `{String}` | `[hash:base64]` | Configure the generated ident |
118
+ | **[`context`](#context)** | `{String}` | `undefined` | Allow to redefine basic loader context for local ident name |
119
+ | **[`hashPrefix`](#hashprefix)** | `{String}` | `undefined` | Allow to add custom hash to generate more unique classes |
120
+ | **[`getLocalIdent`](#getlocalident)** | `{Function}` | `undefined` | Configure the function to generate classname based on a different schema |
121
+ | **[`sourceMap`](#sourcemap)** | `{Boolean}` | `false` | Enable/Disable Sourcemaps |
122
+ | **[`camelCase`](#camelcase)** | `{Boolean\|String}` | `false` | Export Classnames in CamelCase |
123
+ | **[`importLoaders`](#importloaders)** | `{Number}` | `0` | Number of loaders applied before CSS loader |
124
+ | **[`exportOnlyLocals`](#exportonlylocals)** | `{Boolean}` | `false` | Export only locals |
127
125
 
128
126
  ### `url`
129
127
 
130
128
  Type: `Boolean|Function`
131
129
  Default: `true`
132
130
 
133
- Control `url()` resolving. Absolute urls are not resolving.
131
+ Control `url()` resolving. Absolute URLs and root-relative URLs are not resolving.
134
132
 
135
133
  Examples resolutions:
136
134
 
@@ -466,7 +464,66 @@ module.exports = {
466
464
  };
467
465
  ```
468
466
 
467
+ ### `context`
468
+
469
+ Type: `String`
470
+ Default: `undefined`
471
+
472
+ Allow to redefine basic loader context for local ident name.
473
+ By default we use `rootContext` of loader.
474
+
475
+ **webpack.config.js**
476
+
477
+ ```js
478
+ module.exports = {
479
+ module: {
480
+ rules: [
481
+ {
482
+ test: /\.css$/,
483
+ loader: 'css-loader',
484
+ options: {
485
+ modules: true,
486
+ context: path.resolve(__dirname, 'context'),
487
+ },
488
+ },
489
+ ],
490
+ },
491
+ };
492
+ ```
493
+
494
+ ### `hashPrefix`
495
+
496
+ Type: `String`
497
+ Default: `undefined`
498
+
499
+ Allow to add custom hash to generate more unique classes.
500
+
501
+ **webpack.config.js**
502
+
503
+ ```js
504
+ module.exports = {
505
+ module: {
506
+ rules: [
507
+ {
508
+ test: /\.css$/,
509
+ loader: 'css-loader',
510
+ options: {
511
+ modules: true,
512
+ hashPrefix: 'hash',
513
+ },
514
+ },
515
+ ],
516
+ },
517
+ };
518
+ ```
519
+
520
+ ### `getLocalIdent`
521
+
522
+ Type: `Function`
523
+ Default: `undefined`
524
+
469
525
  You can also specify the absolute path to your custom `getLocalIdent` function to generate classname based on a different schema.
526
+ By default we use built-in function to generate a classname.
470
527
 
471
528
  **webpack.config.js**
472
529
 
@@ -479,9 +536,6 @@ module.exports = {
479
536
  loader: 'css-loader',
480
537
  options: {
481
538
  modules: true,
482
- context: path.resolve(__dirname, 'context'), // Allow to redefine basic loader context for `local-ident-name`
483
- hashPrefix: 'hash', // Allow to add custom hash to generate more unique classes
484
- localIdentName: '[path][name]__[local]--[hash:base64:5]',
485
539
  getLocalIdent: (context, localIdentName, localName, options) => {
486
540
  return 'whatever_random_class_name';
487
541
  },
@@ -495,7 +549,7 @@ module.exports = {
495
549
  ### `sourceMap`
496
550
 
497
551
  Type: `Boolean`
498
- Default: `true`
552
+ Default: `false`
499
553
 
500
554
  To include source maps set the `sourceMap` option.
501
555
 
@@ -659,7 +713,20 @@ module.exports = {
659
713
  ### Extract
660
714
 
661
715
  For production builds it's recommended to extract the CSS from your bundle being able to use parallel loading of CSS/JS resources later on.
662
- This can be achieved by using the [mini-css-extract-plugin](https://github.com/webpack-contrib/mini-css-extract-plugin) to extract the CSS when running in production mode.
716
+
717
+ - This can be achieved by using the [mini-css-extract-plugin](https://github.com/webpack-contrib/mini-css-extract-plugin) to extract the CSS when running in production mode.
718
+
719
+ - As an alternative, if seeking better development performance and css outputs that mimic production. [extract-css-chunks-webpack-plugin](https://github.com/faceyspacey/extract-css-chunks-webpack-plugin) offers a hot module reload friendly, extended version of mini-css-extract-plugin. HMR real CSS files in dev, works like mini-css in non-dev
720
+
721
+ ## Contributing
722
+
723
+ Please take a moment to read our contributing guidelines if you haven't yet done so.
724
+
725
+ [CONTRIBUTING](./.github/CONTRIBUTING.md)
726
+
727
+ ## License
728
+
729
+ [MIT](./LICENSE)
663
730
 
664
731
  [npm]: https://img.shields.io/npm/v/css-loader.svg
665
732
  [npm-url]: https://npmjs.com/package/css-loader
package/dist/index.js CHANGED
@@ -21,7 +21,7 @@ var _postcssModulesValues = _interopRequireDefault(require("postcss-modules-valu
21
21
 
22
22
  var _loaderUtils = require("loader-utils");
23
23
 
24
- var _camelCase = _interopRequireDefault(require("lodash/camelCase"));
24
+ var _normalizePath = _interopRequireDefault(require("normalize-path"));
25
25
 
26
26
  var _options = _interopRequireDefault(require("./options.json"));
27
27
 
@@ -48,13 +48,24 @@ function loader(content, map, meta) {
48
48
 
49
49
  if (sourceMap) {
50
50
  if (map) {
51
+ // Some loader emit source map as string
52
+ // Strip any JSON XSSI avoidance prefix from the string (as documented in the source maps specification), and then parse the string as JSON.
51
53
  if (typeof map === 'string') {
52
- map = JSON.stringify(map);
54
+ map = JSON.parse(map.replace(/^\)]}'[^\n]*\n/, ''));
55
+ } // Source maps should use forward slash because it is URLs (https://github.com/mozilla/source-map/issues/91)
56
+ // We should normalize path because previous loaders like `sass-loader` using backslash when generate source map
57
+
58
+
59
+ if (map.file) {
60
+ map.file = (0, _normalizePath.default)(map.file);
61
+ }
62
+
63
+ if (map.sourceRoot) {
64
+ map.sourceRoot = (0, _normalizePath.default)(map.sourceRoot);
53
65
  }
54
66
 
55
67
  if (map.sources) {
56
- map.sources = map.sources.map(source => source.replace(/\\/g, '/'));
57
- map.sourceRoot = '';
68
+ map.sources = map.sources.map(source => (0, _normalizePath.default)(source));
58
69
  }
59
70
  }
60
71
  } else {
@@ -110,12 +121,10 @@ function loader(content, map, meta) {
110
121
 
111
122
  plugins.push((0, _plugins.icssParser)());
112
123
  (0, _postcss.default)(plugins).process(content, {
113
- // we need a prefix to avoid path rewriting of PostCSS
114
- from: `/css-loader!${(0, _loaderUtils.getRemainingRequest)(this).split('!').pop()}`,
124
+ from: (0, _loaderUtils.getRemainingRequest)(this).split('!').pop(),
115
125
  to: (0, _loaderUtils.getCurrentRequest)(this).split('!').pop(),
116
126
  map: options.sourceMap ? {
117
127
  prev: map,
118
- sourcesContent: true,
119
128
  inline: false,
120
129
  annotation: false
121
130
  } : null
@@ -165,7 +174,7 @@ function loader(content, map, meta) {
165
174
  switch (options.camelCase) {
166
175
  case true:
167
176
  addEntry(key);
168
- targetKey = (0, _camelCase.default)(key);
177
+ targetKey = (0, _utils.camelCase)(key);
169
178
 
170
179
  if (targetKey !== key) {
171
180
  addEntry(targetKey);
@@ -184,7 +193,7 @@ function loader(content, map, meta) {
184
193
  break;
185
194
 
186
195
  case 'only':
187
- addEntry((0, _camelCase.default)(key));
196
+ addEntry((0, _utils.camelCase)(key));
188
197
  break;
189
198
 
190
199
  case 'dashesOnly':
@@ -230,32 +239,18 @@ function loader(content, map, meta) {
230
239
  } = message;
231
240
  const {
232
241
  url,
233
- placeholder
242
+ placeholder,
243
+ needQuotes
234
244
  } = item; // Remove `#hash` and `?#hash` from `require`
235
245
 
236
246
  const [normalizedUrl, singleQuery, hashValue] = url.split(/(\?)?#/);
237
247
  const hash = singleQuery || hashValue ? `"${singleQuery ? '?' : ''}${hashValue ? `#${hashValue}` : ''}"` : '';
238
- imports.push(`var ${placeholder} = urlEscape(require(${(0, _loaderUtils.stringifyRequest)(this, (0, _loaderUtils.urlToRequest)(normalizedUrl))})${hash ? ` + ${hash}` : ''});`);
248
+ imports.push(`var ${placeholder} = urlEscape(require(${(0, _loaderUtils.stringifyRequest)(this, (0, _loaderUtils.urlToRequest)(normalizedUrl))})${hash ? ` + ${hash}` : ''}${needQuotes ? ', true' : ''});`);
239
249
  cssAsString = cssAsString.replace(new RegExp(placeholder, 'g'), () => `" + ${placeholder} + "`);
240
250
  });
241
- let newMap = result.map;
242
-
243
- if (sourceMap && newMap) {
244
- // Add a SourceMap
245
- newMap = newMap.toJSON();
246
-
247
- if (newMap.sources) {
248
- newMap.sources = newMap.sources.map(source => source.split('!').pop().replace(/\\/g, '/'), this);
249
- newMap.sourceRoot = '';
250
- }
251
-
252
- newMap.file = newMap.file.split('!').pop().replace(/\\/g, '/');
253
- newMap = JSON.stringify(newMap);
254
- }
255
-
256
251
  const runtimeCode = `exports = module.exports = require(${(0, _loaderUtils.stringifyRequest)(this, require.resolve('./runtime/api'))})(${!!sourceMap});\n`;
257
252
  const importCode = imports.length > 0 ? `// Imports\n${imports.join('\n')}\n\n` : '';
258
- const moduleCode = `// Module\nexports.push([module.id, ${cssAsString}, ""${newMap ? `,${newMap}` : ''}]);\n\n`;
253
+ const moduleCode = `// Module\nexports.push([module.id, ${cssAsString}, ""${result.map ? `,${result.map}` : ''}]);\n\n`;
259
254
  const exportsCode = exports.length > 0 ? `// Exports\nexports.locals = {\n${exports.join(',\n')}\n};` : ''; // Embed runtime
260
255
 
261
256
  return callback(null, runtimeCode + importCode + moduleCode + exportsCode);
package/dist/options.json CHANGED
@@ -52,7 +52,14 @@
52
52
  "type": "string"
53
53
  },
54
54
  "getLocalIdent": {
55
- "instanceof": "Function"
55
+ "anyOf": [
56
+ {
57
+ "type": "boolean"
58
+ },
59
+ {
60
+ "instanceof": "Function"
61
+ }
62
+ ]
56
63
  },
57
64
  "sourceMap": {
58
65
  "type": "boolean"
@@ -78,8 +78,12 @@ var _default = _postcss.default.plugin(pluginName, () => function process(css, r
78
78
  }); // Replace tokens in at-rules
79
79
 
80
80
  css.walkAtRules(atrule => {
81
- // eslint-disable-next-line no-param-reassign
82
- atrule.params = replaceImportsInString(atrule.params.toString());
81
+ // Due reusing `ast` from `postcss-loader` some plugins may lack
82
+ // `params` property, we need to account for this possibility
83
+ if (atrule.params) {
84
+ // eslint-disable-next-line no-param-reassign
85
+ atrule.params = replaceImportsInString(atrule.params.toString());
86
+ }
83
87
  }); // Replace tokens in export
84
88
 
85
89
  Object.keys(exports).forEach(exportName => {
@@ -12,40 +12,58 @@ var _postcssValueParser = _interopRequireDefault(require("postcss-value-parser")
12
12
  function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
13
13
 
14
14
  const pluginName = 'postcss-url-parser';
15
+ const isUrlFunc = /url/i;
16
+ const isImageSetFunc = /^(?:-webkit-)?image-set$/i;
17
+ const needParseDecl = /(?:url|(?:-webkit-)?image-set)\(/i;
15
18
 
16
- function getArg(nodes) {
17
- return nodes.length !== 0 && nodes[0].type === 'string' ? nodes[0].value : _postcssValueParser.default.stringify(nodes);
19
+ function getNodeFromUrlFunc(node) {
20
+ return node.nodes && node.nodes[0];
21
+ }
22
+
23
+ function getUrlFromUrlFunc(node) {
24
+ return node.nodes.length !== 0 && node.nodes[0].type === 'string' ? node.nodes[0].value : _postcssValueParser.default.stringify(node.nodes);
18
25
  }
19
26
 
20
27
  function walkUrls(parsed, callback) {
21
28
  parsed.walk(node => {
22
- if (node.type !== 'function' || node.value.toLowerCase() !== 'url') {
29
+ if (node.type !== 'function') {
23
30
  return;
24
31
  }
25
- /* eslint-disable */
26
32
 
33
+ if (isUrlFunc.test(node.value)) {
34
+ callback(getNodeFromUrlFunc(node), getUrlFromUrlFunc(node), false); // Do not traverse inside `url`
35
+ // eslint-disable-next-line consistent-return
36
+
37
+ return false;
38
+ }
27
39
 
28
- node.before = '';
29
- node.after = '';
30
- /* eslint-enable */
40
+ if (isImageSetFunc.test(node.value)) {
41
+ node.nodes.forEach(nNode => {
42
+ if (nNode.type === 'function' && isUrlFunc.test(nNode.value)) {
43
+ callback(getNodeFromUrlFunc(nNode), getUrlFromUrlFunc(nNode), false);
44
+ }
31
45
 
32
- callback(node, getArg(node.nodes)); // Do not traverse inside url
33
- // eslint-disable-next-line consistent-return
46
+ if (nNode.type === 'string') {
47
+ callback(nNode, nNode.value, true);
48
+ }
49
+ }); // Do not traverse inside `image-set`
50
+ // eslint-disable-next-line consistent-return
34
51
 
35
- return false;
52
+ return false;
53
+ }
36
54
  });
37
55
  }
38
56
 
39
57
  function walkDeclsWithUrl(css, result, filter) {
40
58
  const items = [];
41
59
  css.walkDecls(decl => {
42
- if (!/url\(/i.test(decl.value)) {
60
+ if (!needParseDecl.test(decl.value)) {
43
61
  return;
44
62
  }
45
63
 
46
64
  const parsed = (0, _postcssValueParser.default)(decl.value);
47
65
  const urls = [];
48
- walkUrls(parsed, (node, url) => {
66
+ walkUrls(parsed, (node, url, needQuotes) => {
49
67
  if (url.trim().replace(/\\[\r\n]/g, '').length === 0) {
50
68
  result.warn(`Unable to find uri in '${decl.toString()}'`, {
51
69
  node: decl
@@ -57,7 +75,10 @@ function walkDeclsWithUrl(css, result, filter) {
57
75
  return;
58
76
  }
59
77
 
60
- urls.push(url);
78
+ urls.push({
79
+ url,
80
+ needQuotes
81
+ });
61
82
  });
62
83
 
63
84
  if (urls.length === 0) {
@@ -73,48 +94,62 @@ function walkDeclsWithUrl(css, result, filter) {
73
94
  return items;
74
95
  }
75
96
 
97
+ function uniqWith(array, comparator) {
98
+ return array.reduce((acc, d) => !acc.some(item => comparator(d, item)) ? [...acc, d] : acc, []);
99
+ }
100
+
76
101
  function flatten(array) {
77
- return array.reduce((acc, d) => [...acc, ...d], []);
102
+ return array.reduce((a, b) => a.concat(b), []);
78
103
  }
79
104
 
80
- function uniq(array) {
81
- return array.reduce((acc, d) => acc.indexOf(d) === -1 ? [...acc, d] : acc, []);
105
+ function isEqual(value, other) {
106
+ return value.url === other.url && value.needQuotes === other.needQuotes;
82
107
  }
83
108
 
84
109
  var _default = _postcss.default.plugin(pluginName, (options = {}) => function process(css, result) {
85
110
  const traversed = walkDeclsWithUrl(css, result, options.filter);
86
- const paths = uniq(flatten(traversed.map(item => item.urls)));
111
+ const paths = uniqWith(flatten(traversed.map(item => item.urls)), isEqual);
87
112
 
88
113
  if (paths.length === 0) {
89
114
  return;
90
115
  }
91
116
 
92
- const urls = {};
117
+ const placeholders = [];
93
118
  paths.forEach((path, index) => {
94
119
  const placeholder = `___CSS_LOADER_URL___${index}___`;
95
- urls[path] = placeholder;
120
+ const {
121
+ url,
122
+ needQuotes
123
+ } = path;
124
+ placeholders.push({
125
+ placeholder,
126
+ path
127
+ });
96
128
  result.messages.push({
97
129
  pluginName,
98
130
  type: 'url',
99
131
  item: {
100
- url: path,
101
- placeholder
132
+ url,
133
+ placeholder,
134
+ needQuotes
102
135
  }
103
136
  });
104
137
  });
105
138
  traversed.forEach(item => {
106
- walkUrls(item.parsed, (node, url) => {
107
- const value = urls[url];
139
+ walkUrls(item.parsed, (node, url, needQuotes) => {
140
+ const value = placeholders.find(placeholder => placeholder.path.url === url && placeholder.path.needQuotes === needQuotes);
108
141
 
109
142
  if (!value) {
110
143
  return;
111
- } // eslint-disable-next-line no-param-reassign
144
+ }
145
+
146
+ const {
147
+ placeholder
148
+ } = value; // eslint-disable-next-line no-param-reassign
112
149
 
150
+ node.type = 'word'; // eslint-disable-next-line no-param-reassign
113
151
 
114
- node.nodes = [{
115
- type: 'word',
116
- value
117
- }];
152
+ node.value = placeholder;
118
153
  }); // eslint-disable-next-line no-param-reassign
119
154
 
120
155
  item.decl.value = item.parsed.toString();
@@ -1,6 +1,6 @@
1
1
  "use strict";
2
2
 
3
- module.exports = function escape(url) {
3
+ module.exports = function escape(url, needQuotes) {
4
4
  if (typeof url !== 'string') {
5
5
  return url;
6
6
  } // If url is already wrapped in quotes, remove them
@@ -12,7 +12,7 @@ module.exports = function escape(url) {
12
12
  // See https://drafts.csswg.org/css-values-3/#urls
13
13
 
14
14
 
15
- if (/["'() \t\n]/.test(url)) {
15
+ if (/["'() \t\n]/.test(url) || needQuotes) {
16
16
  return '"' + url.replace(/"/g, '\\"').replace(/\n/g, '\\n') + '"';
17
17
  }
18
18
 
package/dist/utils.js CHANGED
@@ -5,12 +5,15 @@ Object.defineProperty(exports, "__esModule", {
5
5
  });
6
6
  exports.getImportPrefix = getImportPrefix;
7
7
  exports.getLocalIdent = getLocalIdent;
8
+ exports.camelCase = camelCase;
8
9
  exports.dashesCamelCase = dashesCamelCase;
9
10
  exports.getFilter = getFilter;
10
11
  exports.placholderRegExps = void 0;
11
12
 
12
13
  var _path = _interopRequireDefault(require("path"));
13
14
 
15
+ var _camelcase = _interopRequireDefault(require("camelcase"));
16
+
14
17
  var _loaderUtils = _interopRequireDefault(require("loader-utils"));
15
18
 
16
19
  function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
@@ -19,6 +22,8 @@ function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { de
19
22
  MIT License http://www.opensource.org/licenses/mit-license.php
20
23
  Author Tobias Koppers @sokra
21
24
  */
25
+
26
+ /* eslint-disable line-comment-position */
22
27
  const placholderRegExps = {
23
28
  importItemG: /___CSS_LOADER_IMPORT___([0-9]+)___/g,
24
29
  importItem: /___CSS_LOADER_IMPORT___([0-9]+)___/
@@ -35,10 +40,30 @@ function getImportPrefix(loaderContext, importLoaders) {
35
40
  return `-!${loadersRequest}!`;
36
41
  }
37
42
 
43
+ function camelCase(str) {
44
+ return (0, _camelcase.default)(str);
45
+ }
46
+
38
47
  function dashesCamelCase(str) {
39
48
  return str.replace(/-+(\w)/g, (match, firstLetter) => firstLetter.toUpperCase());
40
49
  }
41
50
 
51
+ const whitespace = '[\\x20\\t\\r\\n\\f]';
52
+ const unescapeRegExp = new RegExp(`\\\\([\\da-f]{1,6}${whitespace}?|(${whitespace})|.)`, 'ig');
53
+
54
+ function unescape(str) {
55
+ return str.replace(unescapeRegExp, (_, escaped, escapedWhitespace) => {
56
+ const high = `0x${escaped}` - 0x10000; // NaN means non-codepoint
57
+ // Workaround erroneous numeric interpretation of +"0x"
58
+ // eslint-disable-next-line no-self-compare
59
+
60
+ return high !== high || escapedWhitespace ? escaped : high < 0 ? // BMP codepoint
61
+ String.fromCharCode(high + 0x10000) : // Supplemental Plane codepoint (surrogate pair)
62
+ // eslint-disable-next-line no-bitwise
63
+ String.fromCharCode(high >> 10 | 0xd800, high & 0x3ff | 0xdc00);
64
+ });
65
+ }
66
+
42
67
  function getLocalIdent(loaderContext, localIdentName, localName, options) {
43
68
  if (!options.context) {
44
69
  // eslint-disable-next-line no-param-reassign
@@ -48,7 +73,7 @@ function getLocalIdent(loaderContext, localIdentName, localName, options) {
48
73
  const request = _path.default.relative(options.context, loaderContext.resourcePath).replace(/\\/g, '/'); // eslint-disable-next-line no-param-reassign
49
74
 
50
75
 
51
- options.content = `${options.hashPrefix + request}+${localName}`; // eslint-disable-next-line no-param-reassign
76
+ options.content = `${options.hashPrefix + request}+${unescape(localName)}`; // eslint-disable-next-line no-param-reassign
52
77
 
53
78
  localIdentName = localIdentName.replace(/\[local\]/gi, localName);
54
79
 
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "css-loader",
3
- "version": "2.0.0",
3
+ "version": "2.1.1",
4
4
  "description": "css loader module for webpack",
5
5
  "license": "MIT",
6
6
  "repository": "webpack-contrib/css-loader",
@@ -9,24 +9,28 @@
9
9
  "bugs": "https://github.com/webpack-contrib/css-loader/issues",
10
10
  "main": "dist/cjs.js",
11
11
  "engines": {
12
- "node": ">= 6.9.0 <7.0.0 || >= 8.9.0"
12
+ "node": ">= 6.9.0"
13
13
  },
14
14
  "scripts": {
15
15
  "start": "npm run build -- -w",
16
+ "prebuild": "npm run clean",
16
17
  "build": "cross-env NODE_ENV=production babel src -d dist --ignore 'src/**/*.test.js' --copy-files",
17
18
  "clean": "del-cli dist",
19
+ "commitlint": "commitlint",
20
+ "commitmsg": "commitlint -e $GIT_PARAMS",
18
21
  "lint": "eslint --cache src test",
19
- "prebuild": "npm run clean",
20
22
  "prepublish": "npm run build",
21
23
  "release": "standard-version",
22
24
  "security": "npm audit",
23
- "test": "jest",
25
+ "test:only": "jest",
24
26
  "test:watch": "jest --watch",
25
27
  "test:coverage": "jest --collectCoverageFrom='src/**/*.js' --coverage",
28
+ "pretest": "npm run lint",
29
+ "test": "npm run test:only",
26
30
  "ci:lint": "npm run lint && npm run security",
27
- "ci:lint:commits": "commitlint --from=${CIRCLE_BRANCH} --to=${CIRCLE_SHA1}",
28
- "ci:test": "npm run test -- --runInBand",
31
+ "ci:test": "npm run test:only -- --runInBand",
29
32
  "ci:coverage": "npm run test:coverage -- --runInBand",
33
+ "ci:lint:commits": "commitlint --from=origin/master --to=${CIRCLE_SHA1}",
30
34
  "defaults": "webpack-defaults"
31
35
  },
32
36
  "files": [
@@ -38,13 +42,14 @@
38
42
  "webpack": "^4.0.0"
39
43
  },
40
44
  "dependencies": {
41
- "icss-utils": "^4.0.0",
42
- "loader-utils": "^1.0.2",
43
- "lodash": "^4.17.11",
44
- "postcss": "^7.0.6",
45
+ "icss-utils": "^4.1.0",
46
+ "loader-utils": "^1.2.3",
47
+ "camelcase": "^5.2.0",
48
+ "normalize-path": "^3.0.0",
49
+ "postcss": "^7.0.14",
45
50
  "postcss-modules-extract-imports": "^2.0.0",
46
- "postcss-modules-local-by-default": "^2.0.2",
47
- "postcss-modules-scope": "^2.0.0",
51
+ "postcss-modules-local-by-default": "^2.0.6",
52
+ "postcss-modules-scope": "^2.1.0",
48
53
  "postcss-modules-values": "^2.0.0",
49
54
  "postcss-value-parser": "^3.3.0",
50
55
  "schema-utils": "^1.0.0"
@@ -56,18 +61,18 @@
56
61
  "@babel/preset-env": "^7.1.6",
57
62
  "@commitlint/cli": "^7.2.1",
58
63
  "@commitlint/config-conventional": "^7.1.2",
64
+ "@webpack-contrib/defaults": "^3.0.0",
59
65
  "@webpack-contrib/eslint-config-webpack": "^3.0.0",
60
- "babel-core": "^7.0.0-bridge.0",
61
- "babel-jest": "^23.6.0",
66
+ "babel-jest": "^24.1.0",
62
67
  "cross-env": "^5.2.0",
63
- "del": "^3.0.0",
68
+ "del": "^4.0.0",
64
69
  "del-cli": "^1.1.0",
65
70
  "eslint": "^5.9.0",
66
71
  "eslint-plugin-import": "^2.14.0",
67
72
  "eslint-plugin-prettier": "^3.0.0",
68
- "file-loader": "^2.0.0",
73
+ "file-loader": "^3.0.1",
69
74
  "husky": "^1.2.0",
70
- "jest": "^23.6.0",
75
+ "jest": "^24.1.0",
71
76
  "lint-staged": "^8.1.0",
72
77
  "memory-fs": "^0.4.1",
73
78
  "postcss-loader": "^3.0.0",
@@ -75,10 +80,9 @@
75
80
  "prettier": "^1.15.2",
76
81
  "sass": "^1.15.1",
77
82
  "sass-loader": "^7.1.0",
78
- "standard-version": "^4.0.0",
83
+ "standard-version": "^5.0.0",
79
84
  "strip-ansi": "^5.0.0",
80
- "webpack": "^4.26.1",
81
- "webpack-defaults": "^2.3.0"
85
+ "webpack": "^4.26.1"
82
86
  },
83
87
  "keywords": [
84
88
  "webpack",
@@ -115,5 +119,10 @@
115
119
  "extends": [
116
120
  "@commitlint/config-conventional"
117
121
  ]
122
+ },
123
+ "prettier": {
124
+ "singleQuote": true,
125
+ "trailingComma": "es5",
126
+ "arrowParens": "always"
118
127
  }
119
128
  }