| [9af201e] | 1 | "use strict";
|
|---|
| 2 |
|
|---|
| 3 | Object.defineProperty(exports, "__esModule", {
|
|---|
| 4 | value: true
|
|---|
| 5 | });
|
|---|
| 6 | exports.default = void 0;
|
|---|
| 7 | var _postcssValueParser = _interopRequireDefault(require("postcss-value-parser"));
|
|---|
| 8 | var _utils = require("../utils");
|
|---|
| 9 | function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
|
|---|
| 10 | const isUrlFunc = /url/i;
|
|---|
| 11 | const isImageSetFunc = /^(?:-webkit-)?image-set$/i;
|
|---|
| 12 | const needParseDeclaration = /(?:url|(?:-webkit-)?image-set)\(/i;
|
|---|
| 13 | function getNodeFromUrlFunc(node) {
|
|---|
| 14 | return node.nodes && node.nodes[0];
|
|---|
| 15 | }
|
|---|
| 16 | function getWebpackIgnoreCommentValue(index, nodes, inBetween) {
|
|---|
| 17 | if (index === 0 && typeof inBetween !== "undefined") {
|
|---|
| 18 | return inBetween;
|
|---|
| 19 | }
|
|---|
| 20 | let prevValueNode = nodes[index - 1];
|
|---|
| 21 | if (!prevValueNode) {
|
|---|
| 22 | // eslint-disable-next-line consistent-return
|
|---|
| 23 | return;
|
|---|
| 24 | }
|
|---|
| 25 | if (prevValueNode.type === "space") {
|
|---|
| 26 | if (!nodes[index - 2]) {
|
|---|
| 27 | // eslint-disable-next-line consistent-return
|
|---|
| 28 | return;
|
|---|
| 29 | }
|
|---|
| 30 | prevValueNode = nodes[index - 2];
|
|---|
| 31 | }
|
|---|
| 32 | if (prevValueNode.type !== "comment") {
|
|---|
| 33 | // eslint-disable-next-line consistent-return
|
|---|
| 34 | return;
|
|---|
| 35 | }
|
|---|
| 36 | const matched = prevValueNode.value.match(_utils.WEBPACK_IGNORE_COMMENT_REGEXP);
|
|---|
| 37 | return matched && matched[2] === "true";
|
|---|
| 38 | }
|
|---|
| 39 | function shouldHandleURL(url, declaration, result, options) {
|
|---|
| 40 | if (url.length === 0) {
|
|---|
| 41 | result.warn(`Unable to find uri in '${declaration.toString()}'`, {
|
|---|
| 42 | node: declaration
|
|---|
| 43 | });
|
|---|
| 44 | return {
|
|---|
| 45 | requestable: false,
|
|---|
| 46 | needResolve: false
|
|---|
| 47 | };
|
|---|
| 48 | }
|
|---|
| 49 | return (0, _utils.isURLRequestable)(url, options);
|
|---|
| 50 | }
|
|---|
| 51 | function parseDeclaration(declaration, key, result, options) {
|
|---|
| 52 | if (!needParseDeclaration.test(declaration[key])) {
|
|---|
| 53 | return;
|
|---|
| 54 | }
|
|---|
| 55 | const parsed = (0, _postcssValueParser.default)(declaration.raws && declaration.raws.value && declaration.raws.value.raw ? declaration.raws.value.raw : declaration[key]);
|
|---|
| 56 | let inBetween;
|
|---|
| 57 | if (declaration.raws && declaration.raws.between) {
|
|---|
| 58 | const lastCommentIndex = declaration.raws.between.lastIndexOf("/*");
|
|---|
| 59 | const matched = declaration.raws.between.slice(lastCommentIndex).match(_utils.WEBPACK_IGNORE_COMMENT_REGEXP);
|
|---|
| 60 | if (matched) {
|
|---|
| 61 | inBetween = matched[2] === "true";
|
|---|
| 62 | }
|
|---|
| 63 | }
|
|---|
| 64 | let isIgnoreOnDeclaration = false;
|
|---|
| 65 | const prevNode = declaration.prev();
|
|---|
| 66 | if (prevNode && prevNode.type === "comment") {
|
|---|
| 67 | const matched = prevNode.text.match(_utils.WEBPACK_IGNORE_COMMENT_REGEXP);
|
|---|
| 68 | if (matched) {
|
|---|
| 69 | isIgnoreOnDeclaration = matched[2] === "true";
|
|---|
| 70 | }
|
|---|
| 71 | }
|
|---|
| 72 | let needIgnore;
|
|---|
| 73 | const parsedURLs = [];
|
|---|
| 74 | parsed.walk((valueNode, index, valueNodes) => {
|
|---|
| 75 | if (valueNode.type !== "function") {
|
|---|
| 76 | return;
|
|---|
| 77 | }
|
|---|
| 78 | if (isUrlFunc.test(valueNode.value)) {
|
|---|
| 79 | needIgnore = getWebpackIgnoreCommentValue(index, valueNodes, inBetween);
|
|---|
| 80 | if (isIgnoreOnDeclaration && typeof needIgnore === "undefined" || needIgnore) {
|
|---|
| 81 | if (needIgnore) {
|
|---|
| 82 | // eslint-disable-next-line no-undefined
|
|---|
| 83 | needIgnore = undefined;
|
|---|
| 84 | }
|
|---|
| 85 | return;
|
|---|
| 86 | }
|
|---|
| 87 | const {
|
|---|
| 88 | nodes
|
|---|
| 89 | } = valueNode;
|
|---|
| 90 | const isStringValue = nodes.length !== 0 && nodes[0].type === "string";
|
|---|
| 91 | let url = isStringValue ? nodes[0].value : _postcssValueParser.default.stringify(nodes);
|
|---|
| 92 | url = (0, _utils.normalizeUrl)(url, isStringValue);
|
|---|
| 93 | const {
|
|---|
| 94 | requestable,
|
|---|
| 95 | needResolve
|
|---|
| 96 | } = shouldHandleURL(url, declaration, result, options);
|
|---|
| 97 |
|
|---|
| 98 | // Do not traverse inside `url`
|
|---|
| 99 | if (!requestable) {
|
|---|
| 100 | // eslint-disable-next-line consistent-return
|
|---|
| 101 | return false;
|
|---|
| 102 | }
|
|---|
| 103 | const queryParts = url.split("!");
|
|---|
| 104 | let prefix;
|
|---|
| 105 | if (queryParts.length > 1) {
|
|---|
| 106 | url = queryParts.pop();
|
|---|
| 107 | prefix = queryParts.join("!");
|
|---|
| 108 | }
|
|---|
| 109 | parsedURLs.push({
|
|---|
| 110 | declaration,
|
|---|
| 111 | parsed,
|
|---|
| 112 | node: getNodeFromUrlFunc(valueNode),
|
|---|
| 113 | prefix,
|
|---|
| 114 | url,
|
|---|
| 115 | needQuotes: false,
|
|---|
| 116 | needResolve
|
|---|
| 117 | });
|
|---|
| 118 |
|
|---|
| 119 | // eslint-disable-next-line consistent-return
|
|---|
| 120 | return false;
|
|---|
| 121 | } else if (isImageSetFunc.test(valueNode.value)) {
|
|---|
| 122 | for (const [innerIndex, nNode] of valueNode.nodes.entries()) {
|
|---|
| 123 | const {
|
|---|
| 124 | type,
|
|---|
| 125 | value
|
|---|
| 126 | } = nNode;
|
|---|
| 127 | if (type === "function" && isUrlFunc.test(value)) {
|
|---|
| 128 | needIgnore = getWebpackIgnoreCommentValue(innerIndex, valueNode.nodes);
|
|---|
| 129 | if (isIgnoreOnDeclaration && typeof needIgnore === "undefined" || needIgnore) {
|
|---|
| 130 | if (needIgnore) {
|
|---|
| 131 | // eslint-disable-next-line no-undefined
|
|---|
| 132 | needIgnore = undefined;
|
|---|
| 133 | }
|
|---|
| 134 |
|
|---|
| 135 | // eslint-disable-next-line no-continue
|
|---|
| 136 | continue;
|
|---|
| 137 | }
|
|---|
| 138 | const {
|
|---|
| 139 | nodes
|
|---|
| 140 | } = nNode;
|
|---|
| 141 | const isStringValue = nodes.length !== 0 && nodes[0].type === "string";
|
|---|
| 142 | let url = isStringValue ? nodes[0].value : _postcssValueParser.default.stringify(nodes);
|
|---|
| 143 | url = (0, _utils.normalizeUrl)(url, isStringValue);
|
|---|
| 144 | const {
|
|---|
| 145 | requestable,
|
|---|
| 146 | needResolve
|
|---|
| 147 | } = shouldHandleURL(url, declaration, result, options);
|
|---|
| 148 |
|
|---|
| 149 | // Do not traverse inside `url`
|
|---|
| 150 | if (!requestable) {
|
|---|
| 151 | // eslint-disable-next-line consistent-return
|
|---|
| 152 | return false;
|
|---|
| 153 | }
|
|---|
| 154 | const queryParts = url.split("!");
|
|---|
| 155 | let prefix;
|
|---|
| 156 | if (queryParts.length > 1) {
|
|---|
| 157 | url = queryParts.pop();
|
|---|
| 158 | prefix = queryParts.join("!");
|
|---|
| 159 | }
|
|---|
| 160 | parsedURLs.push({
|
|---|
| 161 | declaration,
|
|---|
| 162 | parsed,
|
|---|
| 163 | node: getNodeFromUrlFunc(nNode),
|
|---|
| 164 | prefix,
|
|---|
| 165 | url,
|
|---|
| 166 | needQuotes: false,
|
|---|
| 167 | needResolve
|
|---|
| 168 | });
|
|---|
| 169 | } else if (type === "string") {
|
|---|
| 170 | needIgnore = getWebpackIgnoreCommentValue(innerIndex, valueNode.nodes);
|
|---|
| 171 | if (isIgnoreOnDeclaration && typeof needIgnore === "undefined" || needIgnore) {
|
|---|
| 172 | if (needIgnore) {
|
|---|
| 173 | // eslint-disable-next-line no-undefined
|
|---|
| 174 | needIgnore = undefined;
|
|---|
| 175 | }
|
|---|
| 176 |
|
|---|
| 177 | // eslint-disable-next-line no-continue
|
|---|
| 178 | continue;
|
|---|
| 179 | }
|
|---|
| 180 | let url = (0, _utils.normalizeUrl)(value, true);
|
|---|
| 181 | const {
|
|---|
| 182 | requestable,
|
|---|
| 183 | needResolve
|
|---|
| 184 | } = shouldHandleURL(url, declaration, result, options);
|
|---|
| 185 |
|
|---|
| 186 | // Do not traverse inside `url`
|
|---|
| 187 | if (!requestable) {
|
|---|
| 188 | // eslint-disable-next-line consistent-return
|
|---|
| 189 | return false;
|
|---|
| 190 | }
|
|---|
| 191 | const queryParts = url.split("!");
|
|---|
| 192 | let prefix;
|
|---|
| 193 | if (queryParts.length > 1) {
|
|---|
| 194 | url = queryParts.pop();
|
|---|
| 195 | prefix = queryParts.join("!");
|
|---|
| 196 | }
|
|---|
| 197 | parsedURLs.push({
|
|---|
| 198 | declaration,
|
|---|
| 199 | parsed,
|
|---|
| 200 | node: nNode,
|
|---|
| 201 | prefix,
|
|---|
| 202 | url,
|
|---|
| 203 | needQuotes: true,
|
|---|
| 204 | needResolve
|
|---|
| 205 | });
|
|---|
| 206 | }
|
|---|
| 207 | }
|
|---|
| 208 |
|
|---|
| 209 | // Do not traverse inside `image-set`
|
|---|
| 210 | // eslint-disable-next-line consistent-return
|
|---|
| 211 | return false;
|
|---|
| 212 | }
|
|---|
| 213 | });
|
|---|
| 214 |
|
|---|
| 215 | // eslint-disable-next-line consistent-return
|
|---|
| 216 | return parsedURLs;
|
|---|
| 217 | }
|
|---|
| 218 | const plugin = (options = {}) => {
|
|---|
| 219 | return {
|
|---|
| 220 | postcssPlugin: "postcss-url-parser",
|
|---|
| 221 | prepare(result) {
|
|---|
| 222 | const parsedDeclarations = [];
|
|---|
| 223 | return {
|
|---|
| 224 | Declaration(declaration) {
|
|---|
| 225 | const {
|
|---|
| 226 | isSupportDataURL,
|
|---|
| 227 | isSupportAbsoluteURL
|
|---|
| 228 | } = options;
|
|---|
| 229 | const parsedURL = parseDeclaration(declaration, "value", result, {
|
|---|
| 230 | isSupportDataURL,
|
|---|
| 231 | isSupportAbsoluteURL
|
|---|
| 232 | });
|
|---|
| 233 | if (!parsedURL) {
|
|---|
| 234 | return;
|
|---|
| 235 | }
|
|---|
| 236 | parsedDeclarations.push(...parsedURL);
|
|---|
| 237 | },
|
|---|
| 238 | async OnceExit() {
|
|---|
| 239 | if (parsedDeclarations.length === 0) {
|
|---|
| 240 | return;
|
|---|
| 241 | }
|
|---|
| 242 | const resolvedDeclarations = await Promise.all(parsedDeclarations.map(async parsedDeclaration => {
|
|---|
| 243 | const {
|
|---|
| 244 | url,
|
|---|
| 245 | needResolve
|
|---|
| 246 | } = parsedDeclaration;
|
|---|
| 247 | if (options.filter) {
|
|---|
| 248 | const needKeep = await options.filter(url);
|
|---|
| 249 | if (!needKeep) {
|
|---|
| 250 | // eslint-disable-next-line consistent-return
|
|---|
| 251 | return;
|
|---|
| 252 | }
|
|---|
| 253 | }
|
|---|
| 254 | if (!needResolve) {
|
|---|
| 255 | // eslint-disable-next-line consistent-return
|
|---|
| 256 | return parsedDeclaration;
|
|---|
| 257 | }
|
|---|
| 258 | const splittedUrl = url.split(/(\?)?#/);
|
|---|
| 259 | const [pathname, query, hashOrQuery] = splittedUrl;
|
|---|
| 260 | let hash = query ? "?" : "";
|
|---|
| 261 | hash += hashOrQuery ? `#${hashOrQuery}` : "";
|
|---|
| 262 | const {
|
|---|
| 263 | resolver,
|
|---|
| 264 | rootContext
|
|---|
| 265 | } = options;
|
|---|
| 266 | const request = (0, _utils.requestify)(pathname, rootContext, Boolean(resolver));
|
|---|
| 267 | if (!resolver) {
|
|---|
| 268 | // eslint-disable-next-line consistent-return
|
|---|
| 269 | return {
|
|---|
| 270 | ...parsedDeclaration,
|
|---|
| 271 | url: request,
|
|---|
| 272 | hash
|
|---|
| 273 | };
|
|---|
| 274 | }
|
|---|
| 275 | const resolvedURL = await (0, _utils.resolveRequests)(resolver, options.context, [...new Set([request, url])]);
|
|---|
| 276 | if (!resolvedURL) {
|
|---|
| 277 | // eslint-disable-next-line consistent-return
|
|---|
| 278 | return;
|
|---|
| 279 | }
|
|---|
| 280 |
|
|---|
| 281 | // eslint-disable-next-line consistent-return
|
|---|
| 282 | return {
|
|---|
| 283 | ...parsedDeclaration,
|
|---|
| 284 | url: resolvedURL,
|
|---|
| 285 | hash
|
|---|
| 286 | };
|
|---|
| 287 | }));
|
|---|
| 288 | const urlToNameMap = new Map();
|
|---|
| 289 | const urlToReplacementMap = new Map();
|
|---|
| 290 | let hasUrlImportHelper = false;
|
|---|
| 291 | for (let index = 0; index <= resolvedDeclarations.length - 1; index++) {
|
|---|
| 292 | const item = resolvedDeclarations[index];
|
|---|
| 293 | if (!item) {
|
|---|
| 294 | // eslint-disable-next-line no-continue
|
|---|
| 295 | continue;
|
|---|
| 296 | }
|
|---|
| 297 | if (!hasUrlImportHelper) {
|
|---|
| 298 | options.imports.push({
|
|---|
| 299 | type: "get_url_import",
|
|---|
| 300 | importName: "___CSS_LOADER_GET_URL_IMPORT___",
|
|---|
| 301 | url: options.urlHandler(require.resolve("../runtime/getUrl.js")),
|
|---|
| 302 | index: -1
|
|---|
| 303 | });
|
|---|
| 304 | hasUrlImportHelper = true;
|
|---|
| 305 | }
|
|---|
| 306 | const {
|
|---|
| 307 | url,
|
|---|
| 308 | prefix
|
|---|
| 309 | } = item;
|
|---|
| 310 | const newUrl = prefix ? `${prefix}!${url}` : url;
|
|---|
| 311 | let importName = urlToNameMap.get(newUrl);
|
|---|
| 312 | if (!importName) {
|
|---|
| 313 | importName = `___CSS_LOADER_URL_IMPORT_${urlToNameMap.size}___`;
|
|---|
| 314 | urlToNameMap.set(newUrl, importName);
|
|---|
| 315 | options.imports.push({
|
|---|
| 316 | type: "url",
|
|---|
| 317 | importName,
|
|---|
| 318 | url: options.resolver ? options.urlHandler(newUrl) : JSON.stringify(newUrl),
|
|---|
| 319 | index
|
|---|
| 320 | });
|
|---|
| 321 | }
|
|---|
| 322 | const {
|
|---|
| 323 | hash,
|
|---|
| 324 | needQuotes
|
|---|
| 325 | } = item;
|
|---|
| 326 | const replacementKey = JSON.stringify({
|
|---|
| 327 | newUrl,
|
|---|
| 328 | hash,
|
|---|
| 329 | needQuotes
|
|---|
| 330 | });
|
|---|
| 331 | let replacementName = urlToReplacementMap.get(replacementKey);
|
|---|
| 332 | if (!replacementName) {
|
|---|
| 333 | replacementName = `___CSS_LOADER_URL_REPLACEMENT_${urlToReplacementMap.size}___`;
|
|---|
| 334 | urlToReplacementMap.set(replacementKey, replacementName);
|
|---|
| 335 | options.replacements.push({
|
|---|
| 336 | replacementName,
|
|---|
| 337 | importName,
|
|---|
| 338 | hash,
|
|---|
| 339 | needQuotes
|
|---|
| 340 | });
|
|---|
| 341 | }
|
|---|
| 342 |
|
|---|
| 343 | // eslint-disable-next-line no-param-reassign
|
|---|
| 344 | item.node.type = "word";
|
|---|
| 345 | // eslint-disable-next-line no-param-reassign
|
|---|
| 346 | item.node.value = replacementName;
|
|---|
| 347 | // eslint-disable-next-line no-param-reassign
|
|---|
| 348 | item.declaration.value = item.parsed.toString();
|
|---|
| 349 | }
|
|---|
| 350 | }
|
|---|
| 351 | };
|
|---|
| 352 | }
|
|---|
| 353 | };
|
|---|
| 354 | };
|
|---|
| 355 | plugin.postcss = true;
|
|---|
| 356 | var _default = exports.default = plugin; |
|---|