lightningcss-loader
Version:
Speed up your Webpack build with lightningcss
108 lines (107 loc) • 6.09 kB
JavaScript
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
return new (P || (P = Promise))(function (resolve, reject) {
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
step((generator = generator.apply(thisArg, _arguments || [])).next());
});
};
var __rest = (this && this.__rest) || function (s, e) {
var t = {};
for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p) && e.indexOf(p) < 0)
t[p] = s[p];
if (s != null && typeof Object.getOwnPropertySymbols === "function")
for (var i = 0, p = Object.getOwnPropertySymbols(s); i < p.length; i++) {
if (e.indexOf(p[i]) < 0 && Object.prototype.propertyIsEnumerable.call(s, p[i]))
t[p[i]] = s[p[i]];
}
return t;
};
Object.defineProperty(exports, "__esModule", { value: true });
exports.LightningCssMinifyPlugin = void 0;
// @ts-ignore
const ModuleFilenameHelpers_1 = require("webpack/lib/ModuleFilenameHelpers");
const webpack_sources_1 = require("webpack-sources");
const lightningcss_1 = require("lightningcss");
const interface_1 = require("./interface");
const path_1 = require("path");
const utils_1 = require("./utils");
const buffer_1 = require("buffer");
const pkgPath = (0, path_1.join)(__dirname, '../package.json');
const pkg = require(pkgPath);
const PLUGIN_NAME = 'lightning-css-minify';
const CSS_FILE_REG = /\.css(?:\?.*)?$/i;
class LightningCssMinifyPlugin {
constructor(opts = {}) {
var _a;
const { implementation } = opts, otherOpts = __rest(opts, ["implementation"]);
if (implementation && typeof implementation.transform !== 'function') {
throw new TypeError(`[LightningCssMinifyPlugin]: implementation.transform must be an 'lightningcss' transform function. Received ${typeof implementation.transform}`);
}
this.transform = (_a = implementation === null || implementation === void 0 ? void 0 : implementation.transform) !== null && _a !== void 0 ? _a : lightningcss_1.transform;
this.options = otherOpts;
}
apply(compiler) {
const meta = JSON.stringify({
name: pkg.name,
version: pkg.version,
options: this.options,
});
compiler.hooks.compilation.tap(PLUGIN_NAME, (compilation) => {
compilation.hooks.chunkHash.tap(PLUGIN_NAME, (_, hash) => hash.update(meta));
if ((0, utils_1.isWebpack5)(compilation)) {
compilation.hooks.processAssets.tapPromise({
name: PLUGIN_NAME,
stage: compilation.constructor.PROCESS_ASSETS_STAGE_OPTIMIZE_SIZE,
additionalAssets: true,
}, () => __awaiter(this, void 0, void 0, function* () { return yield this.transformAssets(compilation); }));
compilation.hooks.statsPrinter.tap(PLUGIN_NAME, (statsPrinter) => {
statsPrinter.hooks.print
.for('asset.info.minimized')
// @ts-ignore
.tap(PLUGIN_NAME, (minimized, { green, formatFlag }) => {
// @ts-ignore
return minimized ? green(formatFlag('minimized')) : undefined;
});
});
}
else {
compilation.hooks.optimizeChunkAssets.tapPromise(PLUGIN_NAME, () => __awaiter(this, void 0, void 0, function* () { return yield this.transformAssets(compilation); }));
}
});
}
transformAssets(compilation) {
return __awaiter(this, void 0, void 0, function* () {
const { options: { devtool }, } = compilation.compiler;
const sourcemap = this.options.sourceMap === undefined
? (devtool && devtool.includes('source-map'))
: this.options.sourceMap;
const _a = this.options, { include, exclude, test: testRegExp, targets: userTargets, features: transformFeatureOptions } = _a, transformOptions = __rest(_a, ["include", "exclude", "test", "targets", "features"]);
const assets = compilation.getAssets().filter((asset) =>
// Filter out already minimized
!asset.info.minimized &&
// Filter out by file type
(testRegExp || CSS_FILE_REG).test(asset.name) &&
(0, ModuleFilenameHelpers_1.matchObject)({ include, exclude }, asset.name));
yield Promise.all(assets.map((asset) => __awaiter(this, void 0, void 0, function* () {
const { source, map } = asset.source.sourceAndMap();
const sourceAsString = source.toString();
const code = typeof source === 'string' ? buffer_1.Buffer.from(source) : source;
const targets = (0, utils_1.getTargets)({
default: userTargets,
key: interface_1.ECacheKey.minify,
});
const result = yield this.transform(Object.assign(Object.assign({ filename: asset.name, code, minify: true, sourceMap: sourcemap, targets }, transformFeatureOptions), transformOptions));
const codeString = result.code.toString();
compilation.updateAsset(asset.name,
// @ts-ignore
sourcemap
? new webpack_sources_1.SourceMapSource(codeString, asset.name, JSON.parse(result.map.toString()), sourceAsString, map, true)
: new webpack_sources_1.RawSource(codeString), Object.assign(Object.assign({}, asset.info), { minimized: true }));
})));
});
}
}
exports.LightningCssMinifyPlugin = LightningCssMinifyPlugin;
;