Schönen Tag. Mit diesem Beitrag möchte ich eine Reihe von Artikeln über neue Funktionen des kommenden Webpacks 5 starten. Warum möchte ich über Webpack sprechen? Zumindest weil ich mich aktiv an seiner Entwicklung beteilige und mich ständig mit seinen Innenseiten beschäftige. In diesem Beitrag möchte ich über Asset-Module sprechen - eine experimentelle Funktion von Webpack 5, mit der Sie mehrere bekannte Lader entfernen und gleichzeitig deren Nutzen beibehalten können.
Stellen Sie sich vor, wir müssen eine Seite mit Bildern und Stilen zusammenstellen.
Webpack 4-Lösung
Die Webpack 4-Konfiguration für diese Aufgabe sieht möglicherweise folgendermaßen aus:
webpack.config.js
module.exports = {
module: {
rules: [
{
test: /\.svg$/,
use: [
'file-loader',
'svgo-loader'
]
},
{
test: /\.css$/,
use: [
'style-loader',
'css-loader'
]
}
]
}
};
src/index.js
import './styles.css';
src/styles.css
.logo {
background: url("/images/logo.svg") no-repeat;
background-size: cover;
width: 75px;
height: 65px;
}
Fazit:
/dist/main.js
/dist/eb4c5fa504857.svg
Mit diesem Ansatz werden alle SVG - Dateien verarbeitet werden SVGO und mit Datei-Loader im Verzeichnis platziert mit dem Bündel zusammengesetzt und CSS, mit CSS-loader , wird sich in etwa wie folgt:
.logo {
background: url("eb4c5fa504857.svg") no-repeat;
background-size: cover;
width: 75px;
height: 65px;
}
Irgendwann müssen wir möglicherweise unsere Seite optimieren und möchten möglicherweise Bilder direkt in CSS einbinden. Ersetzen Sie dazu file-loader
durch url-loader :
{
test: /\.svg$/,
use: [
- 'file-loader',
+ 'url-loader',
'svgo-loader'
]
},
Fazit:
/dist/main.js
Das kompilierte CSS ändert sich wie folgt:
- background: url("eb4c5fa504857.svg") no-repeat;
+ background: url("data:image/svg+xml;base64,....") no-repeat;
Außerdem möchten wir möglicherweise nur kleine SVG-Dateien (z. B. bis zu 8 KB) inline einbinden und den Rest als separate Dateien belassen. Hierfür url-loader
gibt es eine spezielle Grenzwerteinstellung:
{
test: /\.svg$/,
use: [
- 'url-loader',
+ 'url-loader?limit=8192',
'svgo-loader'
]
},
, svg- 8, svg , url-loader
file-loader
.
, webpack 5 Asset Modules, , url-loader
file-loader
( url-loader
, , limit
).
webpack 5
, , Asset Modules. :
module.exports = {
// ...
+ experiments: {
+ asset: true
+ }
};
.
, svg- asset
, file-loader
url-loader
— , , - :
{
test: /\.svg$/,
- use: [
- 'url-loader?limit=8000',
- 'svgo-loader'
- ]
+ type: 'asset',
+ use: 'svgo-loader'
},
, , type: 'asset'
: 8 ( ), , .
use
.
asset
.
asset/inline
url-loader
. , type: 'asset/inline'
data-url:
{
test: /\.svg$/,
- type: 'asset',
+ type: 'asset/inline',
use: 'svgo-loader'
},
, type: 'asset/inline'
data-url.
, svg- mini-svg-data-uri
, svg data-url, base64, :
+ const miniSVGDataURI = require('mini-svg-data-uri');
// ...
{
test: /\.svg$/,
type: 'asset/inline',
+ generator: {
+ dataUrl(content) {
+ content = content.toString();
+ return miniSVGDataURI(content);
+ }
+ },
use: 'svgo-loader'
},
css:
- background: url("data:image/svg+xml;base64,....") no-repeat;
+ background: url("data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg'....") no-repeat;
data-url.
asset/resource
file-loader. , type: 'asset/resource'
:
{
test: /\.svg$/,
- type: 'asset/inline',
+ type: 'asset/resource',
- generator: {
- dataUrl(content) {
- content = content.toString();
- return miniSVGDataURI(content);
- }
- },
use: 'svgo-loader'
},
, asset/resource
, output.path
( dist
), output.assetModuleFilename
:
module.exports = {
+ output: {
+ assetModuleFilename: 'assets/[name][ext]'
+ },
// ...
};
:
/dist/main.js
/dist/assets/logo.svg
[name]
[hash]
long term caching:
module.exports = {
output: {
- assetModuleFilename: 'assets/[name][ext]'
+ assetModuleFilename: 'assets/[hash][ext]'
},
// ...
};
:
/dist/main.js
/dist/assets/eb4c5fa504857.svg
, asset-. , svg- dist/icons
, asset- dist/assets
:
{
test: /\.svg$/,
type: 'asset/resource',
+ generator: {
+ filename: 'icons/[hash][ext]'
+ },
use: 'svgo-loader'
:
/dist/main.js
/dist/assets/fd441ca8b6d00.png
/dist/icons/eb4c5fa504857.svg
asset/source
raw-loader. , type: 'asset/source'
:
file.txt
hello world
webpack.config.js
module.exports = {
// ...
{
test: /\.svg$/,
type: 'asset/resource',
generator: {
filename: 'icons/[hash][ext]'
},
use: 'svgo-loader'
},
+ {
+ test: /\.txt$/,
+ type: 'asset/source'
+ },
// ...
index.js
import './styles.css';
+ import txt from './file.txt';
+ console.log(txt); // hello world
:
/dist/main.js
/dist/icons/eb4c5fa504857.svg
asset
asset/resource
asset/inline
, - , . , 8, asset/resource
, — asset/inline
.
module.exports = {
// ...
{
test: /\.svg$/,
- type: 'asset/resource',
+ type: 'asset'
- generator: {
- filename: 'icons/[hash][ext]'
- },
use: 'svgo-loader'
},
{
test: /\.txt$/,
type: 'asset/source'
},
// ...
asset/inline
:
{
test: /.svg$/,
type: 'asset',
+ parser: {
+ dataUrlCondition: {
+ maxSize: 20 * 1024 // 20kb
+ }
+ },
use: 'svgo-loader'
},
: Asset Modules webpack 5 " ".
.
webpack 5?
. , webpack 5 beta.13
, . , webpack 5 ( , production).
P.S
webpack 5 webpack. , , ( webpack) -.
Vielen Dank für Ihre Aufmerksamkeit.