[英]Webpack 5 Asset Module (asset/resource) makes all svgs disapper
Webpack 實際上不是我的強項,我今天遇到了一個問題,我完全陷入了一個巨大的項目。
基本上我只是運行了 webpack 分析器,我們的包大小太大了,因為我們的項目構建中有大約 200 個 SVG。 我想提出一個簡單的解決方案來減小包大小並使用 webpack 壓縮 SVG,因為這就是我們正在使用的。 在多次失敗后,我認為它會像包含在內一樣簡單
test: /\.(gif|png|jpe?g|svg)$/i,
type: 'asset/resource',
},
我現在可以看到我的包明顯減少了,但是當我加載項目時我所有的 SVG 都被隱藏了。
可能是什么原因? 還有什么方法可以使用 Webpack 5 壓縮 SVG???
這是整個 webpack 配置
const path = require('path');
const MiniCssExtractPlugin = require('mini-css-extract-plugin');
const ForkTsCheckerWebpackPlugin = require('fork-ts-checker-webpack-plugin');
const SpriteLoaderPlugin = require('svg-sprite-loader/plugin');
const { WebpackManifestPlugin } = require('webpack-manifest-plugin');
const hashSubstr = '.[contenthash:8]';
const svgoPlugins = [
{ cleanUpAttrs: true },
{ removeDoctype: true },
{ removeXMLProcInst: true },
{ removeComments: true },
{ removeMetadata: true },
{ removeDesc: true },
{ removeEditorsNSData: true },
{ removeEmptyAttrs: true },
{ removeHiddenElems: true },
{ removeEmptyText: true },
{ removeEmptyContainers: true },
{ cleanupNumericValues: true },
{ moveElemsAttrsToGroup: true },
{ convertColors: { shorthex: true } },
];
module.exports = (env) => ({
entry: ['./scripts/responsive/index.ts', './scripts/pwa/serviceworker.ts'],
output: {
filename: `[name]${!env.development ? hashSubstr : ''}.js`,
globalObject: 'this',
path: path.resolve(__dirname, './bundles/responsive'),
publicPath: '/',
assetModuleFilename: '[hash][ext][query]',
},
mode: !env.development ? 'production' : 'development',
devtool: 'inline-source-map',
optimization: {
minimize: true,
},
module: {
rules: [
// {
// test: /\.(gif|png|jpe?g|svg)$/i,
// type: 'asset/resource',
// },
{
test: /\.(jsx?|tsx?)$/,
loader: 'babel-loader',
options: {
presets: ['@babel/typescript', '@babel/env'],
},
},
{
test: /\.s[ac]ss$/i,
use: [
{
loader: MiniCssExtractPlugin.loader,
options: {
publicPath: '../',
},
},
{
loader: 'css-loader',
options: {
sourceMap: true,
},
},
{
loader: 'sass-loader',
options: {
sourceMap: true,
},
},
],
},
{
test: /\-colou?r\.svg$/,
type: 'asset/resource',
include: [path.resolve(__dirname, 'Content/responsive/svg')],
use: [
{
loader: 'svg-sprite-loader',
options: {
spriteFilename: 'sprite.svg',
esModule: false,
symbolId: (fileName) => {
return `r-icon-${path.basename(fileName, '.svg')}`;
},
},
},
{
loader: 'svgo-loader',
options: {
plugins: svgoPlugins,
},
},
],
},
{
test: /\.svg$/,
type: 'asset/resource',
exclude: /-colou?r\.svg$/,
include: [path.resolve(__dirname, 'Content/responsive/svg')],
use: [
{
loader: 'svg-sprite-loader',
options: {
spriteFilename: 'sprite.svg',
esModule: false,
symbolId: (fileName) => {
return `r-icon-${path.basename(fileName, '.svg')}`;
},
},
},
{
loader: 'svgo-loader',
options: {
plugins: [
{
removeAttrs: {
attrs: '(?!mask).*:(stroke|fill)',
},
},
...svgoPlugins,
],
},
},
],
},
],
},
//stats: 'verbose',
plugins: [
new ForkTsCheckerWebpackPlugin(),
new WebpackManifestPlugin({
fileName: 'asset-manifest.json',
generate: (seed, files) => {
const manifestFiles = files.reduce((manifest, file) => {
manifest[file.name] = file.path;
return manifest;
}, seed);
const entrypointFiles = files
.filter((x) => x.isInitial && !x.name.endsWith('.map'))
.map((x) => x.path);
return {
files: manifestFiles,
entrypoints: entrypointFiles,
};
},
}),
new MiniCssExtractPlugin({
// Options similar to the same options in webpackOptions.output
// both options are optional
filename: `css/[name]${!env.development ? hashSubstr : ''}.css`,
chunkFilename: `css/[id]${!env.development ? hashSubstr : ''}.css`,
}),
new SpriteLoaderPlugin({
plainSprite: true,
}),
],
resolve: {
extensions: ['.js', '.jsx', '.ts', '.tsx'],
alias: {
Svg: path.resolve(__dirname, './Content/responsive/svg'),
},
},
});
就我而言,似乎在使用type: 'asset/resource'
時,模塊被導出為 commonjs 而不是 esmodule 的默認導入
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.