Что такое Webpack и для чего он нужен?

· JavaScript и Блог · 5 мин чтения

В этой записи я расскажу вам что такое Webpack, для чего он нужен и как начать им пользоваться.Я не стал придумывать новый велосипед, поэтому взял официальную документацию проекта. Я лишь постараюсь описать все еще проще чем у них.

Для понимаю этой записи вам нужно иметь хотя бы базовое понимание HTML и JavaScript.

Основы

Давайте создадим новую папку, например webpack-first. Вы можете это сделать где угодно, я сделаю это в /var/www/.

$ mkdir webpack-first && cd webpack-first

Важно! Не называйте папку «webpack», иначе у вас будет выдавать ошибку, из-за конфликта имен. Поэтому в имени папки и присутствует «-first».

Пример ошибки:

npm ERR! code ENOSELF
npm ERR! Refusing to install package with name "webpack" under a package
npm ERR! also called "webpack". Did you name your project the same
npm ERR! as the dependency you're installing?
npm ERR! 
npm ERR! For more information, see:
npm ERR!     <https://docs.npmjs.com/cli/install#limitations-of-npms-install-algorithm>

Далее нужно инициализировать (создать) конфиг для работы с npm:

$ npm init -y

И используя npm установить webpack:

$ npm install --save-dev webpack

После установки у нас должна быть следующая структура внутри папки webpack-first:

  |- package.json
+ |- index.html
+ |- /src
+   |- index.js

«+» — это файлы, которые нам нужно будет сейчас создать.

index.js:

function component() {
  var element = document.createElement('div');

  // Lodash на данные момент подключено через скрипт тэг, это обязательно, чтобы строка ниже работала как надо
  element.innerHTML = _.join(['Привет', 'webpack'], ' ');

  return element;
}

document.body.appendChild(component());

index.html:

<html>
  <head>
    <title>Основы</title>
    <script src="https://unpkg.com/lodash@4.16.6"></script>
  </head>
  <body>
    <script src="./src/index.js"></script>
  </body>
</html>

В этом примере у нас зависимость между <script> тегами. Нам нужно подключить lodash (в head) скрипт, чтобы index.js работал без ошибок.

В такой архитектуре веб-приложения есть недостатки:

  • не сразу понятно какой скрипт от чего зависит
  • если скрипт будет удален в будущем, это испортит правильную работу веб-приложения
  • если скрипт подключен, но нигде не используется, браузер все равно скачает его

Давайте теперь посмотрим, как webpack может помочь в решении проблем описанных выше.

Теперь можете открыть эту страницу в браузере (file:///var/www/webpack/index.html), вы должны увидеть следующую страницу:

JavaScript Webpack

Делаем правильно

Для начала нужно немного подправить структуру проекта. Разделить на источник (src) и то, что мы будет показывать пользователям (dist). В /src будет храниться исходный код, после завершения работы над проектом, все скрипты будут перенесены в dist, включая все нужные зависимости, но об этом чуть ниже.

  |- package.json
+ |- /dist
+   |- index.html
- |- index.html
  |- /src
    |- index.js

Как видно из новой структуры выше, мы создали папку /dist и перенесли туда index.html.

Теперь чтобы завернуть lodash используя webpack, нужно установить локально:

$ npm install --save lodash

И теперь это можно импортировать в src/index.js:

import _ from 'lodash';

function component() {
  var element = document.createElement('div');

  // Lodash теперь имспортируется внутри скрипта
  element.innerHTML = _.join(['Привет', 'webpack'], ' ');

  return element;
}

document.body.appendChild(component());

Мы изменили 2 строки: 1 и 6. На первой строке импортируем lodash. А на 6 просто замени комментарий на более актуальный.

Ну и конечно же нужно зайти в dist/index.html и сделать соответствующие изменения.

Новая версия файл выглядит следующим образом:

<html>
  <head>
    <title>Основы</title>
  </head>
  <body>
    <script src="bundle.js"></script>
  </body>
</html>

Первое, я удалил lodash скрипт, который был в голове документа, потому что сейчас мы его импортируем внутри src/index.js.

Второе, я заменил src/index.js на bundle.js, потому что после работы webpack, мы будем генерировать новый JS файл, который будет называется bundle и автоматически перемещать его в папку с dist/index.html.

 

Теперь давайте сгенерируем bundle.js:

$ ./node_modules/.bin/webpack src/index.js dist/bundle.js

Думаю, что тут все понятно. Папка .bin используется для всех банарных библиотек в npm.

В итоге у вас должно выдать что-то похожее на это:

    Asset    Size  Chunks                    Chunk Names
bundle.js  544 kB       0  [emitted]  [big]  main
   [0] ./src/index.js 255 bytes {0} [built]
   [2] (webpack)/buildin/global.js 488 bytes {0} [built]
   [3] (webpack)/buildin/module.js 495 bytes {0} [built]
    + 1 hidden module

Теперь ваша страница будет выглядеть намного чище, зайдите на file:///var/www/webpack/dist/index.html и посмотрите сами:

После webpack, JavaScript

Модульность

import и export стали стандартами в ES2015. В Webpack они используются для добавления нужных библиотек, как мы уже сделали с lodash выше.

Давайте создадим webpack.config.js Webpack конфиг. Назовем его webpack.config.js, теперь структура нашего проекта должна быть следующей:

  |- package.json
+ |- webpack.config.js
  |- /dist
    |- index.html
  |- /src
    |- index.js

webpack.config.js:

const path = require('path');

module.exports = {
  entry: './src/index.js',
  output: {
    filename: 'bundle.js',
    path: path.resolve(__dirname, 'dist')
  }
};
  • entry — это откуда мы будем брать файл-источник для постройки bundle.js
  • output — используется для того, чтобы сказать webpack куда нужно закинуть построенный файл со всеми зависимостями. В данном случае — это будет bundle.js файл и поместить его нужно в dist папку.

Теперь построим проект заново, только уже использую конфиг:

$ ./node_modules/.bin/webpack --config webpack.config.js

Вам не кажется, что постоянно писать эту команды это слешком долго? Вот мне кажется, давайте все упростим, использую npm’ную script настройку в package.json:

В scripts секцию json добавьте данные о построение проекта следующий образом:

{
  "name": "webpack-first",
  "version": "1.0.0",
  "description": "",
  "main": "index.js",
  "scripts": {
    "build": "webpack"
  },
  "keywords": [],
  "author": "",
  "license": "ISC",
  "devDependencies": {
    "webpack": "^3.8.1"
  },
  "dependencies": {
    "lodash": "^4.17.4"
  }
}

Теперь запустим постройку проекта используя npm:

$ npm run build