"use strict"; /** * @license * Copyright Google LLC All Rights Reserved. * * Use of this source code is governed by an MIT-style license that can be * found in the LICENSE file at https://angular.io/license */ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) { if (k2 === undefined) k2 = k; Object.defineProperty(o, k2, { enumerable: true, get: function() { return m[k]; } }); }) : (function(o, m, k, k2) { if (k2 === undefined) k2 = k; o[k2] = m[k]; })); var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) { Object.defineProperty(o, "default", { enumerable: true, value: v }); }) : function(o, v) { o["default"] = v; }); var __importStar = (this && this.__importStar) || function (mod) { if (mod && mod.__esModule) return mod; var result = {}; if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k); __setModuleDefault(result, mod); return result; }; Object.defineProperty(exports, "__esModule", { value: true }); exports.postcss = void 0; const loader_utils_1 = require("loader-utils"); const path = __importStar(require("path")); const url = __importStar(require("url")); function wrapUrl(url) { let wrappedUrl; const hasSingleQuotes = url.indexOf("'") >= 0; if (hasSingleQuotes) { wrappedUrl = `"${url}"`; } else { wrappedUrl = `'${url}'`; } return `url(${wrappedUrl})`; } async function resolve(file, base, resolver) { try { return await resolver('./' + file, base); } catch { return resolver(file, base); } } exports.postcss = true; function default_1(options) { if (!options) { throw new Error('No options were specified to "postcss-cli-resources".'); } const { deployUrl = '', resourcesOutputPath = '', filename, loader, emitFile, extracted, } = options; const process = async (inputUrl, context, resourceCache) => { // If root-relative, absolute or protocol relative url, leave as is if (/^((?:\w+:)?\/\/|data:|chrome:|#)/.test(inputUrl)) { return inputUrl; } if (/^\//.test(inputUrl)) { return inputUrl; } // If starts with a caret, remove and return remainder // this supports bypassing asset processing if (inputUrl.startsWith('^')) { return inputUrl.substr(1); } const cacheKey = path.resolve(context, inputUrl); const cachedUrl = resourceCache.get(cacheKey); if (cachedUrl) { return cachedUrl; } if (inputUrl.startsWith('~')) { inputUrl = inputUrl.substr(1); } const { pathname, hash, search } = url.parse(inputUrl.replace(/\\/g, '/')); const resolver = (file, base) => new Promise((resolve, reject) => { loader.resolve(base, decodeURI(file), (err, result) => { if (err) { reject(err); return; } resolve(result); }); }); const result = await resolve(pathname, context, resolver); return new Promise((resolve, reject) => { loader.fs.readFile(result, (err, content) => { if (err) { reject(err); return; } let outputPath = loader_utils_1.interpolateName({ resourcePath: result }, filename(result), { content, context: loader.context || loader.rootContext, }).replace(/\\|\//g, '-'); if (resourcesOutputPath) { outputPath = path.posix.join(resourcesOutputPath, outputPath); } loader.addDependency(result); if (emitFile) { // eslint-disable-next-line @typescript-eslint/no-non-null-assertion loader.emitFile(outputPath, content, undefined, { sourceFilename: result }); } let outputUrl = outputPath.replace(/\\/g, '/'); if (hash || search) { outputUrl = url.format({ pathname: outputUrl, hash, search }); } if (deployUrl && !extracted) { outputUrl = url.resolve(deployUrl, outputUrl); } resourceCache.set(cacheKey, outputUrl); resolve(outputUrl); }); }); }; const resourceCache = new Map(); const processed = Symbol('postcss-cli-resources'); return { postcssPlugin: 'postcss-cli-resources', async Declaration(decl) { if (!decl.value.includes('url') || processed in decl) { return; } const value = decl.value; const urlRegex = /url\(\s*(?:"([^"]+)"|'([^']+)'|(.+?))\s*\)/g; const segments = []; let match; let lastIndex = 0; let modified = false; // We want to load it relative to the file that imports const inputFile = decl.source && decl.source.input.file; const context = (inputFile && path.dirname(inputFile)) || loader.context; // eslint-disable-next-line no-cond-assign while ((match = urlRegex.exec(value))) { const originalUrl = match[1] || match[2] || match[3]; let processedUrl; try { processedUrl = await process(originalUrl, context, resourceCache); } catch (err) { loader.emitError(decl.error(err.message, { word: originalUrl })); continue; } if (lastIndex < match.index) { segments.push(value.slice(lastIndex, match.index)); } if (!processedUrl || originalUrl === processedUrl) { segments.push(match[0]); } else { segments.push(wrapUrl(processedUrl)); modified = true; } lastIndex = match.index + match[0].length; } if (lastIndex < value.length) { segments.push(value.slice(lastIndex)); } if (modified) { decl.value = segments.join(''); } decl[processed] = true; }, }; } exports.default = default_1;