Webpack이란?
- 여러개의 파일을 브라우저에서 로딩하는 것은 네트워크 비용을 그만큼 사용하게 되어 결국 반응속도가 느려지게 되는 문제점이 발생하고 이외에도 많은 문제점이 있다.
- 이러한 문제를 해결하기 위해 module bundler로 Webpack을 사용한다.
- 쉽게 말해 많은 파일들을 필요한 형태의 하나 또는 여러개의 번들파일로 만들어준다는 것이다.
그럼 왜 Webpack을 사용할까?
1. 네트워크 병목현상을 해결할 수 있다.
- 너무 많은 자바스크립트 파일을 로드하게되면, 네트워크 병목현상에 빠질 수 있다.
- 이때의 해결방법으로 하나의 자바스크립트 파일만을 사용할 수 있지만 이 방법에는 문제점이 있다.
- 그 문제점은 바로 가독성과 유지보수의 효율성이 떨어진다는 것이다.
- 해결방법으로 Webpack과 같은 모듈 번들러를 사용하게 되면 종속성 있는 파일들을 묶어주므로 가독성과 유지보수 효율성을 높이고 네트워크 병목현상을 최소화 할 수 있다.
2. 모듈 단위로 개발이 가능하다.
1. scope에 신경쓰지 않고 개발이 가능하다.
//test1.js
let value = 'a';
console.log(value);
//test2.js
let value = 'b';
console.log(value);
- test1, test2 파일을 HTML 변수가 같은 스코프에 선언되어 충돌이 발생한다.
- 하지만 이때 모듈 번들러를 사용하게 되면 모듈 번들러는 모듈을 즉시실행함수로 변경해주기 때문에, 스코프에 신경쓰지 않고 개발할 수 있다.
2. 라이브러리 종속 순서를 신경 쓰지 않아도 된다.
<script src="util-jquery.js" />
<script src="jquery.js" />
- util-jquery.js 는 jquery를 사용하기 때문에 로드 순서상 jquery.js가 나중에 호출되면 에러가 발생한다.
- 하지만 모듈 번들러를 사용한다면 위와 같은 로드 순서를 신경쓰지 않아도 된다.
3. 코드를 압축/최적화 할 수 있다.
- 앞서 말한 것과 같이 종속성이 있는 파일들을 묶어주기 때문에 Webpack의 Config 또는 플러그인에 따라 코드를 압축/최적화 할 수 있다.
4. ES6 버전 이상의 스크립트를 사용할 수 있다.
- 오래된 버전의 브라우저에서는 ES6이상의 자바스크립트 문법을 사용할 수 없다.
- 하지만 Webpack의 Babel-loader를 사용하면 ES6 이상의 자바스크립트 문법을 ES5 버전의 문법으로 변경시켜주기 때문에 사용가능해진다.
본격적으로 Webpack을 설정 및 학습해보자.
- Webpack 및 babel 설치
npm i -D webpack webpack-cli webpack-dev-server html-webpack-plugin
npm i -D @babel/core @babel/preset-env babel-loader
-D : devDependencies로 설정하여 배포 서버에서는 해당 모듈들을 설치하지 않을 수 있다.
- webpack : 번들러 웹팩의 코어
- webpack-cli : webpack 명령어를 사용할 수 있게 해주는 모듈
- webpack-dev-server : 실시간으로 변경사항을 보여주는 live server
- html-webpack-plugin : html 파일에 번들 파일을 자동으로 추가해주는 플러그인
- @babel/core : transpiler 핵심 모듈
- @babel/preset-env : 브라우저에 필요한 ECMAscript버전을 자동으로 파악해서 알아서 polyfill을 넣어줌
- babel-loader : JSX 및 ES6+ 문법을 transpiling
웹팩3까지는 webpack만 설치해도 되었는데 웹팩4부터는 webpack-cli를 같이 설치해야 커맨드라인에 webpack이란 명령어를 사용할 수 있다. 웹팩은 하나의 설정 파일로 모든걸 해결한다. 이제 설정 파일을 만들자 package.json이 있는 위치에 다음 파일을 만들어줍니다.
webpack.confing.js
// webpack.config.js
const path = require("path");
const HtmlWebpackPlugin = require("html-webpack-plugin");
module.exports = {
mode: "development",
entry: "./src/index.ts", // 번들링 시작 위치
// 여러개의 entry 선언 방법
/*
entry:{
index : '파일 경로' // 파일경로에 index.js 가 생성됨
file : '파일 경로' // 파일경로에 file.js 가 생성됨
또는
app : ['a.js', 'b.js'] // a.js랑 b.js가 한 파일로 엮여 app.js라는 결과물로 나옴
*/
output: {
path: path.join(__dirname, "/dist"), // 번들 결과물 위치
filename: "[name].js", // 이렇게 써줘야 [name]에 entry의 index나 file 문자열이 들어가 index.js file.js로 결과물이 나온다.
// [name].js가 아니라 result.js라고 적으면 그대로 result.js로 결과물이 나온다.
},
module: {
rules: [
{
test: /[\.(ts|tsx)]$/, // .ts나 .tsx 파일을 babel-loader를 이용하여 transpiling
loader: "babel-loader",
exclude: /node_modules/, // node_modules는 빼고
options: {
presets: [
[
"@babel/preset-env",
{
targets: { node: "current" }, // 노드일 경우만
modules: "false", // false로 해야 최신모듈 시스템이 그대로 유지되어서 트리 쉐이킹이 됩니다.
// ES2015모듈 시스템에서 import 되지 않은 export들을 정리해주는 기능이죠. 용량이 많이 줄어들기 때문에 꼭 트리 쉐이킹 사용하자!
useBuiltIns: "usage", // entry 파일 최상단에 넣어둔 import 'core-js/stable'과 import 'regenerator-runtime/runtime'을 자신의 target에 맞게 바꾸어줍니다.
// 'entry' 외에 'usage'와 false도 있는데 개인적으로 'usage'를 제일 선호합니다. 'usage'는 알아서 사용코드를 파악하여 폴리필을 import해줍니다.
//entry 파일 최상단에 import문을 적을 필요가 없습니다. false는 entry 최상단에 넣은 import문을 그냥 그대로 사용합니다. 즉 환경에 따라 polyfill을 다르게 적용하지 않는 것입니다.
},
],
"@babel/preset-react",
"@babel/preset-typescript",
],
},
},
],
},
plugins: [
new HtmlWebpackPlugin({ template: "./src/index.html" }), // 템플릿 위치
],
resolve: {
modules: [path.join(__dirname, "src"), "node_modules"], // 모듈 위치
extensions: [".ts", ".js"],
},
optimization: {
// 웹팩4에서 최적화 관련 플러그인들이 모두 이쪽 속성으로 통합되었습니다.
// 나중에 나오는 CommonsChunkPlugin도 사라지고 여기에 병합되었습니다.
minimize: false, // UglifyJsPlugin을 계승 / mode가 production일 때 자동으로 켜짐
splitChunks: {}, // CommonsChunkPlugin을 계승 / mode가 production일 때 자동으로 켜짐
concatenateModules: true, // ModuleConcatenationPlugin을 계승
},
};
'webpack' 카테고리의 다른 글
[Webpack] 3. CSS 번들링하기 (0) | 2022.10.25 |
---|---|
[Webpack] 2. tsconfig 설정 (0) | 2022.10.25 |