[Webpack] - Plugin

함성준·2021년 7월 13일
0
post-thumbnail

Webpack - Plugin

웹팩 도큐먼트 내용을 요약하기 위한 문서입니다.

Plugin

웹팩 로더가 소스코드에 대한 전처리의 역할을 담당해주고 있다면 플러그인은 로더가 할 수 없는 다른작업을 수행할 목적으로 존재하는 개념입니다. 직접 커스텀하게 플러그인을 개발할 수도 있고 존재하는 플러그인이 매우 많기 때문에 그중 대표적인 일부분만 살펴보도록 하겠습니다.

html-webpack-plugin


이 플러그인은 번들 자바스크립트 파일을 자동적으로 제공될 수 있도록 웹팩 실행시 HTML 파일을 생성하도록 합니다.

간단하게 한번 사용해 보도록 할까요 ?

$ npm install html-webpack-plugin -D
//webpack.config.js
const HtmlWebpackPlugin = require('html-webpack-plugin')

module.exports = {
    ...,
    plugins: [
        new HtmlWebpackPlugin()
    ]
}

별도의 옵션 설정 없이 만들어진 아웃풋 HTML 은 아래와 같습니다.

<!doctype html>
<html>
    <head>
        <meta charset="utf-8">
        <title>Webpack App</title>
        <meta name="viewport" content="width=device-width,initial-scale=1">
        <script defer="defer" src="main.e2830693a67de77494b7.js"></script>
    </head>
    <body>
    </body>
</html>

defer 키워드를 통해 백그라운드에서 다운로드를 실행하고 스크립트는 페이지 렌더링을 블로킹 하지 않도록 설정되어 있는 부분을 확인할 수 있습니다.

여러개의 엔트리가 잡혀있다면 어떻게 될까요 ?

<!doctype html>
<html>
    <head>
        <meta charset="utf-8">
        <title>Webpack App</title>
        <meta name="viewport" content="width=device-width,initial-scale=1">
        <script defer="defer" src="main.de22020bcc99d56acce9.js"></script>
        <script defer="defer" src="main2.bc544f9299ce5df8db03.js"></script>
    </head>
    <body>
    </body>
</html>

엔트리의 갯수만큼 별도의 스크립트 태그로 작성된 것을 확인할 수 있었습니다. 옵션 설정을 통해서 생성되는 HTML 파일의 title, 파일의 이름, 메타 태그, 등을 설정할 수 있는 것으로 보입니다.

MiniCssExtractPlugin


이 플러그인은 어플리케이션에서 작성된 CSS 소스 코드를 번들 자바스크립트에 내장시키지 않고 별도의 파일로 추출할 수 있는 기능을 제공합니다.

바로 예제로 들어가보죠.

디렉토리 구조가 아래와 같을 때, 스크립트 소스에서 스타일시트를 import 해보겠습니다.

$ tree ./src
./src
├── entryOne.css
├── entryOne.ts
├── entryTwo.css
├── entryTwo.ts
import {functionFromA} from './folderOne/moduleA'
import {functionFromB} from './folderOne/moduleB'
import './entryOne.css'
functionFromA()
functionFromB()

별도의 설정을 하지 않았으므로 .css 파일을 해석할 수 있는 로더가 없다고 에러가 발생할 겁니다.

ERROR in ./src/entryOne.css 1:0
Module parse failed: Unexpected token (1:0)
You may need an appropriate loader to handle this file type, currently no loaders are configured to process this file. See https://webpack.js.org/concepts#loaders
> .entryOne {
|     width: auto;
|     height: auto;
 @ ./src/entryOne.ts 3:0-24

스타일 시트를 로드하기 위해서는 어떤 작업을 해야할까요 ? css-loaderstyle-loader 를 설치해야 합니다.

css-loader.css 파일을 해석할 수 있도록 도와주며 style-loader 는 해석한 파일을 DOMstyle 태그를 생성하여 인젝션 하는 역할을 합니다.

$ npm install style-loader css-loader -D

이후 웹팩 설정파일에 로더를 추가하여 오류 없이 번들링 된 것을 확인할 수 있었습니다. 하지만 아직 mini-css-extract-plugin 을 사용하지 않았기 때문에 번들 자바스크립트 파일에 스타일 소스까지 포함된 상태입니다.

./dist
├── assets
│   └── 8e36814b7c56efe8b9d3..png
├── index.html
├── main.4e0e8a00a6a20a151fa8.js
└── main2.fb89bd7bf1bd7904a7eb.js

설정을 추가했습니다.

const MiniCssExtractPlugin = require('mini-css-extract-plugin);
module.exports = {
    ...,
    module: {
        rules: [
            {
                test: /.css$/,
                use: [MiniCssExtractPlugin.loader,'style-loader', 'css-loader'],
                exclude: /node_modules/
            },
        ]
    },
    plugins: [
        new HtmlWebpackPlugin(),
        new MiniCssExtractPlugin()
    ]
}

한번 돌려보죠. 돌리다가 오류가 났습니다. 이게 뭐죠?

ERROR in ./src/entryOne.css
Module build failed (from ./node_modules/mini-css-extract-plugin/dist/loader.js):
ReferenceError: document is not defined

확인해본 결과 style-loader 와 혼용하면 발생하는 에러라고 합니다. 생각해보니 그렇네요. 스타일 로더는 DOM에 인라인으로 인젝션하는 역할을 해주는데 mini-css-extract-plugin 과 같이 사용할 경우 같은 리소스를 중복해서 사용할 위험이 있다는 생각이 들었습니다.

결과적으로 스타일 리소스는 별도의 파일로 분리하는 것에도 성공했습니다. 같이 사용된 html-webpack-plugin 은 분리된 스타일시트 파일의 개수만큼 link 태그를 생성하여 자동적으로 불러오도록 결과 파일을 만들고 있었습니다.

./dist
├── assets
│   └── 8e36814b7c56efe8b9d3..png
├── index.html
├── main.01fcd5b70838f9628435.js
├── main.css
├── main2.5b9640665b4c24e1c8b8.js
└── main2.css
<!DOCTYPE html>
<html>
    <head>
        <meta charset="utf-8">
        <title>Webpack App</title>
        <meta name="viewport" content="width=device-width, initial-scale=1">
        <script defer src="main.01fcd5b70838f9628435.js"></script>
        <script defer src="main2.5b9640665b4c24e1c8b8.js"></script>
        <link href="main.css" rel="stylesheet">
        <link href="main2.css" rel="stylesheet">
    </head>
    <body>
    </body>
</html>

요약하자면,

  • 웹팩 플러그인을 직접 개발할 수 있다.
  • 플러그인의 종류가 너무 많아 머릿속에 전부 넣어두긴 어렵다. 하지만 도큐먼트를 잘 찾아서 필요에 맞게 설정할 역량을 갖출 필요는 있다.
  • 빌드 결과 파일 최적화에 대한 내용은 여기에서 일부 다룬 내용이 있음.
  • 한 플러그인을 소재로 별도의 포스팅을 좋겠다고 생각하는중이다.

0개의 댓글