Webpack 4 и разделение конфигурационного файла на модули
Привет, Хабр! Сегодня я расскажу вам о Webpack 4 с разделением кода на отдельные модули, а также о интересных решениях, которые помогут вам быстрее собрать сборку на webpack 4. В конце, я предоставлю свою базовую сборку на webpack c самыми необходимыми инструментами, которую вы в последствие сможете расширить. Данная сборка вам поможет понять данный материал, а также возможно поможет быстрее написать свою реализацию и быстрее решить возможные проблемы.
Основная идеология данной сборки — это корректное разделения кода внутри конфигурационного файла для удобства использования, чтения и чистоты webpack.config.js. Необходимые модули и плагины для dev и prod версии (а также для разделения функционала в главном файле) будут находиться в отдельной папке webpack и из неё импортироваться для соединения с главным конфигом.
Зачем нужен такой подход?
С постепенным ростом количества модулей, плагинов и т.д, которыми обрастает ваша сборка на вебпаке, конфигурационный файл растёт как на дрожжах. Со временем данный файл становится трудно читаемым, а изменять его под конкретный проект, если какие-то модули в нём не используется становится труднее, а хочется чего-то универсального. Поэтому требуется чёткая организация кода.
Что нам понадобится?
Мы будем использоваться плагин webpack-merge.
Создаём папку webpack и выносим все отдельные модули в отдельные файлы. Например, webpack/pug.js, webpack/scss.js и экспортируем из них эти функции.
Файл pug.js
module.exports = function() {
return {
module: {
rules: [
{
test: /\.pug$/,
loader: 'pug-loader',
options: {
pretty: true,
},
},
],
},
};
};
Файл webpack.config.js. В данном файле мы их подключаем, и с помощью данного плагина удобно и быстро соединяем.
const merge = require('webpack-merge');
const pug = require('./webpack/pug');
const common = merge([
{
entry: {
'index': PATHS.source + '/pages/index/index.js',
'blog': PATHS.source + '/pages/blog/blog.js',
},
output: {
path: PATHS.build,
filename: './js/[name].js',
},
plugins: […],
optimization: { … },
},
pug(),
]);
Теперь если у нас есть новая задача, под которую нужен новый модуль, плагин, лоадер, то мы выносим его в отельный модуль (файл) и помещаем в папку webpack, а затем подключаем его в главный конфигурационный файл, сохраняя конфиг максимально чистым.
Настройки для production и development
Сейчас мы с помощью банального if закончим наше разделение, к которому мы стремились, и настроим наш вебпак под эти два типа разработки, благодаря чему станет окончательно удобно пользоваться данным инструментом, а так же в будущем сможем гибко и просто настраивать его под любой другой проект, или же расширять в текущем. Для экспорта в ноду (для самой работы вебпака) в webpack 4 мы используем следующую конструкцию:
module.exports = function(env, argv) {
if (argv.mode === 'production') {
return merge([
common,
extractCSS(),
favicon(),
]);
}
if (argv.mode === 'development') {
return merge([
common,
devserver(),
sass(),
css(),
sourceMap(),
]);
}
В объект common мы подключаем то, что используется и на проде и в разработке, а в условиях подключаем только те модули, которые необходимы в этих случаях.
Теперь хотелось бы поговорить об основных особенностях webpack 4 относительно webpack 3
- Для быстрого запуска, webpack 4 не нуждается в webpack.config.js, ему теперь необходима лишь точка входа (index.js)
- В новой версии webpack command line interface вынесен в отдельный пакет и нужно установить webpack-cli.
- Для запуска webpack 4, нужно (иначе будет warning) в скриптах указать mode (режим работы) --mode production или --mode development, в зависимости от ключа меняется работа вебпака. Режим development направлен для ускорения сборки. В production варианте направлено всё на итоговую минификацию кода.
- Для того что бы создать common.js и common.css файлы, более не используется CommonsChunkPlugin, за это теперь отвечают splitChunks и используется следующая конструкция:
optimization: { splitChunks: { cacheGroups: { 'common': { minChunks: 2, chunks: 'all', name: 'common', priority: 10, enforce: true, }, }, }, },
В вебпак 3 — это было бы так в plugins:new webpack.optimize.CommonsChunkPlugin({ name: 'common ', })
Соответственно в чанках в HtmlWebpackPlugin подключаем (тут без изменений).plugins: [ new HtmlWebpackPlugin({ filename: 'index.html', chunks: ['index', 'common'], template: PATHS.source + '/pages/index/index.pug', }), ],
- Следующий важный момент, для того чтобы создать sourceMap, теперь мы используем следующий подход — создаём файл sourceMap.js в папке webpack и подключаем в дев версии например (как указано выше):
module.exports = function() { return { devtool: 'eval-sourcemap', }; };
Теперь подход с plugins: [new webpack.optimize.UglifyJsPlugin ({}) ] не работает.
На этом я хотел бы завершить свой рассказ и предоставить свою базовую сборку — ссылка на webpack 4, которая возможно вам поможет в работе и освоение. Спасибо за внимание!