TIL 70 | Webpack 사용하여 개발 환경 구축하기

meow·2020년 10월 18일
0

JavaScript

목록 보기
27/46

리액트 웹팩으로 개발환경 구축하기(without CRA)
How to set up React, Webpack, and Babel: what you will learn
webpack boiler-plate repository

1. 의존성 초기화

프로젝트 폴더 생성 및 package.json을 생성한다.

webpack-react-study 폴더를 생성하고 package.json 파일 생성

$ mkdir webpack-react-study
$ cd webpack-react-study
$ npm init -y

package.json 파일의 내부

{
  "name": "webpack-react-study",
  "version": "1.0.0",
  "main": "index.js",
  "license": "MIT"
}

2. 라이브러리 설치

초기 프로덕션 의존성(production dependencies)와 개발 의존성(development dependencies)을 설치한다. 개발 의존성은 개발 단계에서만 사용되는 의존 라이브러리, 프로덕션 의존성은 배포 단계에서 사용되는 라이브러리를 말한다.

$ yarn add react react-dom
$ yarn add @babel/core babel-loader @babel/preset-env @babel/preset-react css-loader style-loader html-webpack-plugin webpack webpack-dev-server webpack-cli -D

설치된 라이브러리?

react // 리액트
react-dom // 브라우저 DOM을 제어한다. UI를 렌더링할때 사용
@babel/core // babel의 핵심 라이브러리, es6를 es5로 컴파일
babel-loader // babel과 webpack을 사용해서 자바스크립트 파일을 컴파일
@babel/preset-env // es6, es7 버전을 지정안해도 babel이 자동 탐지
@babel/preset-react // 리액트(JSX)를 js로 인식 가능케 함
css-loader // css 파일을 import 또는 require 가능케 함
style-loader // css 파일을 style 태그로 만들어 head에 삽입
html-webpack-plugin // 웹팩 번들에 html 파일을 제공
webpack // 웹팩을 사용
webpack-dev-server // 웹팩 개발 서버를 구동
webpack-cli // 웹팩 커멘드라인을 사용

3. Babel 설정

babel이란 es6 코드를 이전 버전에서 실행가능하도록 변환해주는 컴파일러이다.

프로젝트 최상위 webpack-react-study에 바벨 설정 파일을 만든다.

$ touch .babelrc

.babelrc 파일을 만들어서 아래와 같이 코드를 추가한다. babel 그 자체로는 아무것도 동작하지 않기 때문에 plugin을 설치해야 한다. .babelrc 라는 파일은 바벨에 대한 플러그인을 설정해주는 파일이다.

{
    "presets": ["@babel/preset-env", "@babel/preset-react"]
}

매번 플러그인을 설치하고 등록하기가 귀찮아서 presets 라는 기능을 만들었다. presets이 무엇이냐면 플러그인들을 포함한 번들 파일인데, 한번만 설정하면 자동으로 설치된다.

4. Webpack 설정

webpack.config.js라는 파일을 생성하자.

$ touch webpack.config.js

하단에 아래와 같은 코드를 작성하자!

const webpack = require('webpack');
const HtmlWebpackPlugin = require('html-webpack-plugin');

const port = process.env.PORT || 3000;

module.exports = {
  // webpack 설정 코드 작성. 작성된 코드는 module.export로 내보냅니다.
};

mode

webpack.config.js 파일 안에 아래 코드를 추가한다. mode 옵션은 웹팩 설정이 development 모드인지 production 모드인지 정한다.

...
module.exports = {
  mode: 'development',
};

entry, output

entry 옵션은 앱이 있는 위치와 번들링 프로세스가 시작되는 지점이다. 웹팩4 부터는 entry 옵션을 생략할 수 있다고 한다. 생략할 경우에는 ./src/index.js를 기본으로 가정한다.

output 옵션은 번들링 프로세스가 끝난 뒤 번들링 된 파일을 저장할 장소와 이름을 지정한다. 번들링된 파일 이름을 bundle.[hash].js로 하고, 그 파일을 ./dist에 저장하라는 의미이다.

_filename의 [hash]는 어플리케이션이 수정되어 다시 컴파일될 때마다 웹팩에서 생성된 해시로 변경해 캐싱에 도움이 된다.

module.exports= {
  ...
  entry:'./src/index.js',
  output:{
      path: __dirname + '/dist',
      filename: 'bundle.[hash].js'
  }
}

module

...
module.exports = {
  ...
  module: {
    rules: [

      // 첫 번째 룰
      {
        test: /\.(js)$/,
        exclude: /node_modules/,
        use: ['babel-loader']
      },

      // 두 번째 룰
      {
        test: /\.css$/,
        use: [
          {
            loader: 'style-loader'
          },
          {
            loader: 'css-loader',
            options: {
              modules: true,
              camelCase: true,
            }
          }
        ]
      }
    ]
  },
};

module 옵션은 번들링 과정에서 사용할 규칙을 설정한다. ES6, ES7 문법으로 작성된 JS 파일을 ES5로 바꾸기 위해 작성했던 .babelrcbabel-loader를 이용해 규칙에 적용한다.

node_modules 폴더를 제외한 모든 .js 파일에 babel-loader (.babelrc에 설정한 파일)를 적용한다.

.js 파일에서 import 또는 require로 .css파일을 가져올 수 있게 해주는 css-loader와 .css 파일을 style 태그로 만든 뒤 head 태그 안에 삽입해주는 style-loader를 규칙에 적용한다. css-loader의 option에서 modules는 CSS Module을 사용하는 것을, camelCase는 해당 옵션으로 CSS를 사용할 것을 의미한다.

plugins

plugins 옵션은 웹팩 번들링 과정에 적용할 플러그인을 설정해준다. HtmlWebpackPlugin은 html 파일이나 favicon을 번들링 과정에 포함한다. 예를 들어 번들된 파일 bundle.[hash].js를 index.html에 자동 삽입해준다.

module.exports = {
  ...
  plugins: [
    new HtmlWebpackPlugin({
      template: 'public/index.html',
    })
  ],
};

devServer

devServer 개발 서버를 정의하는 옵션이다. host는 로컬호스트로 지정하고 port는 상단에서 정의한 값으로 설정해준다. open: true은 서버를 시작했을 때 자동으로 브라우저를 열어주는 옵션이고, historyApiFallback은 브라우저에서 URL을 변경할 수 있도록 도와주는 옵션이다.

module.exports = {
  ...
  devServer: {
    host: 'localhost',
    port: port,
    open: true,
    historyApiFallback: true
  }
};

5. 리액트 앱 만들기

먼저 HtmlWebpackPlugin에 사용되는 index.html을 아래와 같이 생성한다.

mkdir public && cd $_ && touch index.html

public/index.html

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <meta http-equiv="X-UA-Compatible" content="ie=edge">
  <title>webpack-react-study</title>
</head>
<body>
  <div id="root"></div>
</body>
</html>

루트 디렉토리로 돌아와 index.js를 생성한다.

$ mkdir src && cd $_ && touch index.js
// src/components/App.js
import React from 'react';
import { mainWrapper } from './App.css';
const App = () => {
    return (
        <div className={mainWrapper}>
            <h1>Hello, Webpack!!! with React</h1>
        </div>
    );
};

export default App;
// src/components/App.css
.main_wrapper {
	background-color: blue;
}
...
"scripts": {
    "start": "webpack-dev-server"
  },
...

package.json 전체 코드는 아래와 같다.

{
  "name": "webpack-react-study",
  "version": "1.0.0",
  "main": "index.js",
  "license": "MIT",
  "scripts": {
    "start": "webpack-dev-server",
    "build": "webpack"
  },
  "dependencies": {
    "react": "^16.13.1",
    "react-dom": "^16.13.1"
  },
  "devDependencies": {
    "@babel/core": "^7.9.0",
    "@babel/preset-env": "^7.9.5",
    "@babel/preset-react": "^7.9.4",
    "babel-loader": "^8.1.0",
    "css-loader": "^3.5.3",
    "html-webpack-plugin": "^4.2.0",
    "webpack": "^4.43.0",
    "webpack-cli": "^3.3.11",
    "webpack-dev-server": "^3.10.3"
  }
}

리액트를 실행한다. 개발 서버를 작동한다!

$ npm start
profile
🌙`、、`ヽ`ヽ`、、ヽヽ、`、ヽ`ヽ`ヽヽ` ヽ`、`ヽ`、ヽ``、ヽ`ヽ`、ヽヽ`ヽ、ヽ `ヽ、ヽヽ`ヽ`、``ヽ`ヽ、ヽ、ヽ`ヽ`ヽ 、ヽ`ヽ`ヽ、ヽ、ヽ`ヽ`ヽ 、ヽ、ヽ、ヽ``、ヽ`、ヽヽ 🚶‍♀ ヽ``ヽ``、ヽ`、

0개의 댓글