이번 포스팅에서는 webpack.config.js 파일을 이용해서 React에서 사용할 webpack 환경설정을 진행해보고자 한다.
기본적으로 webpack은 Nodejs 환경에서 돌아간다. 그렇기 때문에 npm을 이용해 패키지를 설치하고 사용하는 것이 가능하다.
npm init -y
npm install react react-dom
npm install -D webpack webpack-cli
프로젝트 디렉토리 안에서 webpack.config.js 파일을 생성해주자.
src 디렉토리와 dist 디렉토리 역시 생성해준다. src 디렉토리 안에는 webpack이 bundle 할 파일들이 들어가게 된고 dist 디렉토리 안에는 bundle 된 js 파일이 위치하게 된다. 그리고 src 디렉토리 안에는 index.jsx 파일을 생성해 주었다. (추후 해당 파일을 entry 파일로 설정할 것이다.)
cf ) React component를 사용하는 파일의 경우 jsx 확장자를 사용하기도 한다.
babel을 통해 JSX 문법이 구현되기 때문에 webpack.config.js 파일 안에서 JSX를 JavaScript로 변환할 수 있게끔 babel을 세팅해줘야만 한다. 다음과 같은 라이브러리가 필요하다.
👉 webpack 과 babel을 연결해주는 라이브러리
npm install -D babel-loader
👉 옛날 브라우저에서도 구동할 수 있게끔 코드를 바꿔주는 babel 라이브러리
npm install -D @babel/preset-env
👉 JSX를 사용할 수 있게끔 해주는 babel 라이브러리
npm install -D @babel/preset-react
👉 한번에 설치하기
npm install -D babel-loader @babel/preset-env @babel/preset-react
기본적으로 React에서 돌아가는 파일은 1개의 html 파일과 1개의 JavaScript 파일이다. 따라서 src 디렉토리 안에서 코드가 수정될 때마다 bundle 파일을 계속 생성해줘야 한다. (기존의 bundle.js 파일을 덮어쓰는 형태로 작동)
webpack-dev-server를 사용하게 되면 npx webpack을 통해 계속해서 bundle 파일을 생성해줘야만 하는 번거로움을 없앨 수 있다. webpack-dev-server는 웹 서버를 구축해주는 라이브러리이다. 쉽게 말해 index.html 파일을 랜더해주는 웹 서버라고 생각하면 된다. webpack-dev-server는 서버를 돌리기 전에 src 디렉토리 안에 있는 파일을 bundling 해서 dist 디렉토리 안에 최신화시킨다. 그리고 해당 결과물을 가지고 화면에 랜더되는 것을 보여준다. 개발용으로 사용되는 서버이므로 실제 배포를 할 때는 따로 서버를 구축해줘야만 한다.
npm install -D webpack-dev-server
package.json 파일 안의 "script" 부분에 다음과 같은 내용을 추가하여 dev-server를 실행할 수 있는 명령어를 만들어주도록 하자.
"dev" : "webpack server --env development"
마지막으로 src 디렉토리 안의 파일들이 수정되었을 때 페이지가 새로고침 되지 않고 component에서 변경된 부분만 Re-rendering 되게끔 하기 위해 아래의 라이브러리를 설치해주면 된다.
npm install -D @pmmmwh/react-refresh-webpack-plugin
npm install -D react-refresh
아래는 위의 내용들을 토대로 작성된 webpack.config.js 파일의 내용이다.
// webpack.config.js 파일
const path = require('path')
// nodejs 환경에서 돌아가기 때문에 nodejs 내장 패키지를 가져올 수 있다.
const webpackPlugin = require('@pmmmwh/react-refresh-webpack-plugin')
// npm install로 설치한 패키지 역시 가져올 수 있다.
module.exports = {
// name은 webpack의 이름
name: 'react-project',
// mode는 개발모드인지 production 모드인지 등을 구분
mode: 'development',
// 어떤 확장자명을 사용할 것인지 명시해줄 수 있다.
// resolve의 extensions에는 번들할 파일의 확장자 명시
// 특정 확장자 내용을 제거할 수도 있다.
// 확장자명 뿐만 아니라 라이브러리도 명시 가능
resolve: {
extensions: ['.js', '.jsx']
},
// 내가 앞으로 번들 할 파일들
entry: {
// index.jsx 기준으로 require한 것들 전부를 가져오기 때문에 최초 실행할 파일명만 명시해주면 된다.
// 진입점 파일
app: ['./src/index.jsx']
},
// module의 내용을 합쳐서 내보내게 된다.
// entry는 받을 거, output은 내보낼 거
// module은 받으면서 추가적으로 더 넣을 것
module: {
// rules 속성은 배열로 받는다.
// rules 안에서 객체 형태로 내용을 받는다.
// 여러가지의 rule로 바벨을 사용하겠다.
rules: [{
// 확장자가 js 이거나 jsx 일 때 (정규식) babel을 넣는다.
test: /\.jsx?/,
loader: 'babel-loader', // webpack과 babel을 연결해주는 babel 라이브러리
// babel에 대한 옵션내용 추가
options: {
presets: [
// 옛날 브라우저에서도 환경에 맞게 실행해주는 옵션
['@babel/preset-env', { // babel/preset-env의 옵션 설정
targets: {
browsers: [ // browserslist에 알맞는 텍스트 형태로 입력
'last 2 chrome versions',
'> 5% in KR'
]
},
debug: true
}],
'@babel/preset-react' // JSX 사용하기 위해
],
// babel에 대한 plugin
plugins: [
'react-refresh/babel'
]
}
}]
},
// webpack 전체에 대한 plugin
plugins: [
new webpackPlugin()
],
// 내보낼 파일의 위치와 파일명 (번들 한 파일)
output: {
path: path.join(__dirname, 'dist'),
filename: 'bundle.js',
publicPath: '/dist'
},
devServer: {
static: {
directory: path.join(__dirname, 'public') // index.html 파일 위치
},
compress: true,
port: 3000,
hot: true,
historyApiFallback: true // 새로고침 적용
},
}
'React' 카테고리의 다른 글
create-react-app 없이 React 구동하기 (0) | 2022.04.21 |
---|---|
React - css 적용하기 (0) | 2022.04.21 |
React - Webpack (0) | 2022.04.18 |
React - State 끌어올리기 (0) | 2022.04.17 |
React - 리스트와 Key (0) | 2022.04.15 |