webpack
- это сборщик модулей, он анализирует модули приложения и собирает их в один или более бандл(bundle).
В практических уроках далее я буду использовать webpack
, поэтому разбираемся с ним заранее.
Для начала нужно инициализировать npm
командой npm init
.
Для установки вебпака используем команду:
npm i webpack webpack-cli -D
webpack
- это самое главное, сам собрщикwebpack-cli
- это пакет для запуска вебпака из командной строки.Для базового запуска webpack
используем команду:
npx webpack
Дальше при настройке вебпака мы поговорим как лучше запускать его и как создать свою удобную команду с блэкджеком.
У webpack есть два режима работы
Когда мы запускаем проект без
webpack.config.js
наш входной главный файл должен в таком режиме работы обязательно называтьсяindex.js
и находиться в папкеsrc
-src/index.js
.
Все же в реальных проектах всегда используется
webpack.config.js
- файл с помощью которого мы можем сами все гибко настроить.
Создаем в корне проекта файл webpack.config.js
и помещаем в него этот код:
'use strict';
let path = require('path'); // техническая переменная для правильной работы c путями
module.exports = {
mode:'development', // мод в каком режиме мы работаем
entry: './src/index.js', // точка входа
output: { // точка выхода
filename: 'bundle.js',
path: path.resolve(__dirname, 'dist')
},
watch:true, // позволяет автоматически собирать проект при изменениях
devtool:'source-map', // хранит наши исходные файлы
module:{}, // тут будут лоадеры
plugins:[], // тут будут плагины
};
mode
Свойство
mode
имеет два режимаdevelopment
иproduction
:
development
- это режим разработки, в таком режиме сборка будет происходить быстрее. Этот режим не сильно оптимизирует ваш код разными плагинами. Этот режим нужен для процесса работы, а когда уже закончим проект, то ставим вproduction
mode:'development',
production
- Это режим для конечной сборки продукта, если не указыватьmode
, то этот режим ставится автоматически, он сжимает код на столько на сколько возможно и делает его совершенно нечитабельным, но оптимизированным
mode:'production',
entry
Свойство
entry
просто указывает входную точку, тот файл с которого мы будем начинать. В варианте где мы использовали вебпак без конфига, такой файл являетсяindex.js
. Обычно это такой файл, где вы прописываете все импорты, файл который собирает все модули в одном месте.
entry: './src/index.js', // мы тут можем указать путь к нашему файлу и все, необязательно index.js
entry: [ // для двух и более файлов можно сделать массив
'./src/index.js',
'./script.js'
],
output
Здесь мы указываем имя файла в котором будет храниться весь минифицированный код из модулей и путь где он будет лежать.
output: {
filename: 'bundle.js', // имя файла на выходе
path: path.resolve(__dirname, 'dist') // путь
// __dirname - позволяет получить корень нашей папки
// dist - это какая папка будет создана, например можно сделать так '/dist/js'
},
watch
Это свойство в позиции
true
просто позволяет в автоматическом режиме следить за проектом и пересобирать его на ходу, нам не придется каждый раз писатьnpx webpack
. Это свойство можно и не ставить в конфиге. Вpackage.json
в полеscripts
мы можем создать свой скрипт для запуска и слежения.
"scripts": {
"build": "webpack",
"start": "webpack --watch"
},
// в таком случае запускается проект не через npx, а через npm
// npm build - просто соберет проект как и npx webpack
// npm start - соберет проект и запустит сразу watch
devtool
У
devtool
есть разные настройки, но в основном всегда используетсяsource-map
. Эта опция позволяет нам сохранять исходный код. В браузере зайдя в инспектор кода на вкладку source мы можем посмотреть исходные файлы. Они будут на вкладке которая будет иметь имя вашего проекта изpackage.json
, если раскрыть вкладу, вы увидите исходные файлы. Безdevtool:'source-map'
соответственно их там не будет.
devtool:'source-map',
Лоадеры(загрузчик) - это модули, которые нужны что бы взаимодействовать с разными типами файлов при импорте.
В базовом виде webpack понимает только js
и JSON
, что бы исправить такую ситуацию используют лоадеры.
Но сначала их нужно установить.
Для начала css loader
для работы с css
файлами.
npm install --save-dev css-loader
Далее sass loader
для scss
.
npm install --save-dev sass-loader
Без этих лоадеров, при импорте css
или scss
файлов в модулях будут ошибки.
Так же установим babel-loader
который будет наш код компилировать в более старый, такой код понятен для современных бразуеров и для старых браузеров. У babel
много возможностей,
в нашем случае за код для старых браузеров отвечает опция @babel/preset-env
npm install -D babel-loader @babel/preset-env
Лоадер состоит из module{}
- свойство содержащее правила и внутри него rules[]
- это уже сами правила. Внутри rules[]
находится объект с несколькими свойствами:
test
- внутри которого путь в виде регулярных выражений и use
- сам лоадер, если их лоадеров несколько, можно указать как массив. Сидеть и запоминать как и что писать не нужно, просто гуглите нужный loader и в документации там будет все написанно.
Теперь настраиваем webpack.config.js
:
module.exports = {
module: { // содержит наши правила
rules: [{ // сами правила
test:/\.(s*)css$/, // путь
use: [ // сами лоадеры, в моем случае сразу два в одном месте
'css-loader', // для css
'sass-loader', // для scss
]
},
{ // правила для babel
test: /\.m?js$/, // путь
exclude: /(node_modules|bower_components)/, // это строчка указывает на исключения
use: { // сами правила. Здесь уже в виде объекта, loader указанно как свойство
loader: 'babel-loader', // сам лоадер
options: { // тут доп свойство с опциями
presets: ['@babel/preset-env'] // и опция которая нам нужна
}
} // все это не нужно писать в ручную, все это взято с документаций. гуглите ребята гуглите!
}
],
},
};
Если лоадеры нужны для работы с разными типами файлов при импорте, то плагин позволяет работать не только с импортами.
Плагины так же могут выполнять задачи уже после сборки бандла. Эти задачи могут касаться самого бандла, так и другого кода.
Короче говоря, плагин, штука помощнее.
Установим плагин для минификации css
npm install --save-dev mini-css-extract-plugin
webpack.config.js:
const miniCss = require('mini-css-extract-plugin'); // импортируем сам плагин
module.exports = {
module: {
rules: [{
test:/\.(s*)css$/,
use: [
miniCss.loader, // добавляем в правило у лоадера такое свойство(взято с документации)
'css-loader',
'sass-loader',
]
},
{
test: /\.m?js$/,
exclude: /(node_modules|bower_components)/,
use: {
loader: 'babel-loader',
options: {
presets: ['@babel/preset-env']
}
}
}
],
},
plugins: [ // в plugins все плагины создаются с помощью new
new miniCss({ // у нашего плагина есть опция
filename: 'style.min.css', // опция - имя файла на выходе
}),
]
};
Итог таков, мы имеем настройки для работы с css
,scss
, babel
под старые браузеры, минификацию css
.
const path = require('path');
const miniCss = require('mini-css-extract-plugin');
module.exports = {
mode:'development',
entry: ['./src/index.js'],
output: {
filename: 'bundle.js',
path: path.resolve(__dirname, 'dist')
},
watch:true,
devtool:'source-map',
module: {
rules: [{
test:/\.(s*)css$/,
use: [
miniCss.loader,
'css-loader',
'sass-loader',
]
},
{
test: /\.m?js$/,
exclude: /(node_modules|bower_components)/,
use: {
loader: 'babel-loader',
options: {
presets: ['@babel/preset-env']
}
}
}
],
},
plugins: [
new miniCss({
filename: 'style.min.css',
}),
]
};
Не забываем файлы css
или scss
импортировать в ваш главный файл, в моем случае index.js
.
Ваш минифицированый css
файл будет появляться там же где и js
файл.