* 웹팩 소개
- 지난 장까지는 컴포넌트를 하나만 만들었지만 컴포넌트를 여러개 만들게 되면 스크립트 문서가 너무 복잡해진다. 이렇게되면 코드를 관리하기가 매우 까다롭다.
- 웹팩은 여러 개의 자바스크립트 파일을 하나로 만들어 준다. 이 때 바벨도 적용가능하고 코드를 더 깔끔하게 해준다.
* 웹팩 사용
- 먼저 터미널을 켜서 원하는 폴더 내에서 npm init을 입력해 패키지를 만들어준다.
- 리액트와 리액트 돔도 필요하므로 npm i react react-dom 을 입력하여 설치한다.
- 웹팩을 사용하기 위해서 npm i -D webpack webpack-cli 두가지를 설치한다. 웹팩은 개발환경에서만 사용하므로 -D를 입력하였다.
- webpack.config.js 파일을 만들어준다.
module.exports = {
}
- 위와 같이 작성하고 안에 웹팩의 설정들을 입력하게 된다.
- 다음으로 client.jsx 를 만들어준다. 이를 통해서 렌더링을 진행할 것이다.
const React = require('react');
const ReactDom = require('react-dom');
const WordRelay = require('./WordRelay');
ReactDom.render(<WordRelay/>, document.querySelector('#root'));
- html에서 리액트와 리액트 돔을 불러왔듯이 const require을 이용해서 둘을 불러온다.
- 이렇게하게되면 더 이상 html에서 불러올 필요도 없다. 물론 바벨도 굳이 불러올 필요가 없다.
- 참고로 jsx확장자를 쓴 이유는 js문법 뿐 아니라 jsx문법을 쓴다는 걸 인지 시킴과 동시에 리액트를 사용한다는 것을 나타낸다.
- 컴포넌트를 여기에 입력해도 되지만 가장 위에서 언급했듯이 너무 복잡해지므로 컴포넌트 별로 별도 파일을 만들자.
- 끝말잇기 게임을 만들 예정이므로 WordRelay.jsx 파일을 만든다.
const React = require('react');
const { Component } = React;
class WordRelay extends Component {
state = {
text:'Hello, webpack',
};
render() {
return <h1>{this.state.text}</h1>
}
}
module.exports = WordRelay;
- 리액트를 사용하므로 리액트는 꼭 불러와야한다. 그리고 기존에는 React.Component를 상속 받았지만 위와 같이 const에 미리 선언하면 Component만 사용하도록 줄일 수 있다.
- 컴포넌트를 만들었고, 이 파일 외부에서도 사용가능하도록 노드의 모듈화 시스템으로 exports해주었다.
- 이제 client.jsx에서 이를 불러올 수 있고, 위의 client.jsx 코드를 다시 보게되면 const require로 불러왔음을 알 수 있다.
- 웹팩은 앞서 말한대로 webpack.config.js로 돌아가므로 이를 작성할 필요가 있다.
const path = require('path');
module.exports = {
name: 'word-relay-setting',
mode: 'development', //실서비스 : production
devtool: 'eval',
resolve: {
extensions: ['.js', '.jsx']
},
entry: {
app: ['./client'],
}, // 입력
module: {
rules: [{
test: /\.jsx?/,
loader: 'babel-loader',
options: {
presets: ['@babel/preset-env', '@babel/preset-react'],
plugins: ['@babel/plugin-proposal-class-properties']
}
}],
},
output: {
path: path.join(__dirname, 'dist'), //A:\Documents\Github...
filename: 'app.js'
}, // 출력
};
- name은 이 웹팩설정의 이름이다. 임의로 작성하면 된다.
- 모드는 개발환경이고, devtool은 eval을 작성한다.
- 가장 중요한 것은 entry와 output이다. 이는 어떤파일들을 넣고 어떻게 완성시킬지를 말한다.
- 확장자를 일일히 언급하며 입력에 넣기 번거로우므로 resolve 속성에 extensions로 확장자를 배열형태로 넣어주면 웹팩이 알아서 인식한다.
- entry에서 app: 에 배열로 합칠 파일들을 입력한다. 우리는 client.jsx에서 이미 WordRelay파일을 불러왔으므로 굳이 입력하지 않아도 웹팩이 알아서 합쳐준다.
- output부분에서 app.js를 이 폴더 안 dist라는 폴더안에 만들겠다고 선언해두었다. 먼저 노드에서 경로를 조작하도록 하는 path를 가져왔다. path.join(__dirname, 'dist') 를 입력하여 현재폴더(__dirname으로 표현)와 app.js를 만들 폴더명을 입력한다.
- 이제 바벨을 읽을 수 있도록 패키지를 몇가지 더 설치해야한다.
npm i -D @babel/core
npm i -D @babel/preset-env
npm i -D @babel/preset-react
npm i -D babel-loader
npm i -D @babel/plugin-proposal-class-properties
- 바벨코어는 기본적인 바벨기능이고, env 프리셋은 나의 브라우저 환경에 맞게 알아서 최신문법을 예전 문법으로 바꿔주는 역할을 한다. 리액트 프리셋으로 jsx지원하도록 하였고, 바벨로더로 바벨과 웹팩을 연결하도록 한다. 플러그인은 클래스 컴포넌트에서 오류가 나서 설치하게 되었다.
- 이제 이 설치한 것들을 웹팩 설정에 module:{} 을 통해서 인풋으로 받은 것들을 적용받도록 한다. 이들은 모듈내에서 rules를 통해 배열로 규칙을 정한다.
- test로 규칙을 정할 파일들을 작성하는데 정규 표현식을 이용해서 js와 jsx파일 모두 규칙을 적용시켰다.
- 바벨을 적용하도록 로더에 입력하고, 옵션에 아까 설치한 패키지들을 입력한다.
- 이제 모든 설정이 끝났으므로 터미널에 npx webpack을 입력하면 app.js가 정상적으로 dist폴더에 생성되는 것을 볼 수 있다.
* 바벨로더의 옵션
- 위에서 봤던 것에서 더 나아가 좀 더 웹팩의 설정들을 알아보자.
const path = require('path');
const RefreshWebpackPlugins = require('@pmmmwh/react-refresh-webpack-plugin');
module.exports = {
name: 'word-relay-setting',
mode: 'development', //실서비스 : production
devtool: 'eval',
resolve: {
extensions: ['.js', '.jsx']
},
entry: {
app: ['./client'],
}, // 입력
module: {
rules: [{
test: /\.jsx?/,
loader: 'babel-loader',
options: {
presets: [
['@babel/preset-env', {
targets: {
browsers: ['> 1% in KR'],
},
debug: true,
}],
'@babel/preset-react',
],
plugins: [
'@babel/plugin-proposal-class-properties',
'react-refresh/babel',
]
}
}],
},
plugins:[
new RefreshWebpackPlugins()
],
output: {
path: path.join(__dirname, 'dist'), //A:\Documents\Github...
filename: 'app.js',
publicPath: '/dist/',
}, // 출력
};
- 세부 패키지를 보기 보다는 각 설정의 의미를 알아보고자한다.
- 먼저 우리는 모듈에서 규칙을 배열의 형태로 정한다. 이 때 로더로 바벨로더를 넣어 주었는데 그 아래의 옵션으로 이 바벨로더의 설정을 또 따로 할 수 있다.
- presets에 배열 형태로 env와 react를 넣었었는데 여기서는 preset-env의 설정을 또 별개로 하겠다는 의미이다. babel/preset-env 자체가 preset, 즉 플러그인의 모음이므로 사용하는 플러그인을 줄여서 작업량을 줄일 수 있다.
- targets 속성으로 브라우저 속성을 주어서 원하는 브라우저만 지원하도록 할 수 있다. 여기서 쓰이는 문법은 browserslist에서 확인 가능하다. 위 코드('> 1% in KR' )는 한국에서 1%이상의 점유율을 가진 브라우저만 적용하겠다는 의미이다.
- 그리고 개발의 편의를 위해 debug: true를 주었다.
- 마지막으로 plugins가 별개로 또 있는데, 이는 웹팩에서 스크립트문서들을 합치는 것 외에 다른 기능과 관련된 plugins도 넣을 수 있음을 의미한다.
참고
이 글은 ZeroCho 님의 리액트 무료 강좌를 수강하며 개인적으로 정리하며 쓰는 글입니다.
인프런
유튜브
'Client > React.js' 카테고리의 다른 글
<리액트 기초> 코드 개선하기 (0) | 2021.02.03 |
---|---|
<리액트 기초> 웹팩 데브서버와 핫 리로딩 (0) | 2021.02.01 |
<리액트 기초> 리액트와 Hooks (0) | 2021.01.28 |
<리액트 기초> 메서드와 함수형 setState (2) | 2021.01.26 |
<리액트 기초> 리액트 컴포넌트 (0) | 2021.01.23 |