본문 바로가기

오픈소스/노드

[Node] React 프로젝트를 직접 만들어보기 with Babel, Webpack

 리액트는 Facebook에서 만들고 유지 관리하는 인기있는 JavaScript 라이브러리 입니다. 리액트는 웹 애플리케이션에서 뷰 레이어를 만들기 위한 포괄적인 도구들을 제공하는데 중점 을 둡니다. 리액트는 컴포넌트 개념에 초점을 맞추어 뷰의 추상화를 제공합니다. 컴포넌트는 버튼, 입력 폼, HTML div 와 같은 간단한 컨테이너 혹은 사용자 인터페이스의 다른 요소 일 수 있습니다. 개념은 특정 책임이 있는 재사용성이 높은 컴포넌트를 정의하고 구성하여 애플리케이션의 사용자 인터페이스를 구성할 수 있어야 한다는 것입니다.

 

 이러한 리액트를 사용하기 위해서는 프로젝트를 생성하는 것이 당연지사입니다. 맨 처음 리액트 프로젝트를 생성할 때 많은 사람들은 아래의 명령어를 입력하여 간단하게 프로젝트를 생성하곤 합니다. 

 

create react app

 

 결코 이 명령어가 나쁘다는 표현은 아닙니다. 하지만 가끔 내가 이렇게 만든 프로젝트는 어떻게 해서 동작을 하는 것인지, 왜 이렇게 동작이 되는 것인지 알고 싶은 경우가 있을 것입니다. 오늘은 이러한 리액트 프로젝트의 초기 환경에 대해 알아볼 것입니다. 

 

 서론은 이쯤하고 본격적으로 간단하게 리액트의 사용을 시작할 수 있는 구체적인 프로젝트를 생성해보겠습니다.

 

# Contents


  • 의존성 설치
  • 프로젝트 생성

 

 

# 의존성 설치


 프로젝트의 의존성을 설치하기 위해서는 아래와 같은 기초적인 이론을 갖추어야 합니다.

 

1. 설명

 먼저 프로젝트를 생성하기 전에 리액트 프로젝트 기반이 되는 의존성이 무엇인지 파악하고 그것에 대해 설치를 시작해보도록 하겠습니다. 다음은 리액트 프로젝트를 구성하는데 필요한 의존성 목록입니다.

 

  • react, react-dom, htm : 리액트를 사용하기 위한 라이브러리 입니다.
  • @babel/core babel-loader @babel/preset-react @babel/preset-env : 리액트는 es6버전을 사용하기 때문에 es5 버전으로 변경하는 라이브러리(core) 이며, jsx문법을 javascript로 변경해주는 라이브러리(preset-react) 를 포함하고 있고, 브라우저의 환경 및 시스템 환경에 따라 컴파일을 다르게 해주는 라이브러리(preset-env) 와 플러그인을 통해 babel 사용을 명시해주는 라이브러리(babel-loader) 입니다.
  • webpack webpack-dev-server webpack-cli html-webpack-plugin

 

2. 설치

 리액트를 설치할 때에는 --save 옵션 을 이용하여 현재 모듈에 설치를 해주도록 하겠습니다. 그리고 나머지 라이브러리는 -D 옵션 혹은 --save-dev 옵션 을 통해 개발에서만 적용되도록 설치하겠습니다. npm의 옵션에 관한 내용은 다른 문서를 참고해주시기 바랍니다.

 

 아래 명령어를 통해 의존성을 생성합니다.

 

npm init -y
npm install --save react react-dom htm
npm install --save-dev @babel/core babel-loader @babel/preset-react @babel/preset-env webpack webpack-dev-server webpack-cli html-webpack-plugin

 

 설치가 성공적으로 되셨으면 본격적으로 프로젝트를 생성 해보도록 하겠습니다.

 

 

# 프로젝트 생성


 본 프로젝트는 JSX 문법을 JavaScript로 변경하는 플로그인을 사용하고 있으나, 범용 JavaScript 애플리케이션의 맥락에서 클라이언트 측과 서버 측 코드 모두에서 작업을 수행해야 한다는 목표를 정하고 있기 때문에 HTM 라이브러리 를 사용하고 있습니다. 따라서 HTM 라이브러리를 이용한 리액트 문법은 다소 복잡하거나 의아할 수 있습니다.

 

1. src/index.html

 먼저 최상위 홈페이지의 파일 입니다. 리액트는 컴포넌트 형태 로 표현되기 때문에 id 혹은 Tag에 위치에 컴포넌트를 삽입할 수 있습니다. 현재 이 코드는 id 값인 app이 있습니다. 이 app이 리액트 컴포넌트의 결과 값으로 삽입 되는 것입니다. 여기서 결과 값이라기 보다는 render라는 표현이 맞는 표현이라고 생각하지만 처음 배우신 분은 리턴 값이라고 생각하시면 됩니다.

 

<!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>My React App</title>
    </head>
    <body>
        abcdefg ... <br />
        <div id="app"></div>
    </body>
</html>

 

2. src/index.js

 리액트의 컴포넌트입니다. 해당 파일에서는 템플릿 태그 함수 htm을 통하여 리액트 엘리먼트 를 생성합니다. 리액트 엘리먼트에서는 컴포넌트를 생성하고 가상의 리액트 돔 에 추가합니다. 리액트 돔에 추가한 것은 방금 생성한 엘리먼트이고, getElementById를 통하여 app을 찾아 결과 값을 render 하는 역할입니다. 코드는 아래와 같습니다.

 

import react from "react";
import ReactDOM from "react-dom";
import htm from "htm";

const html = htm.bind(react.createElement);
class Hello extends react.Component {
    render() {
        return html`<h1>Hello ${this.props.name} World</h1>`;
    }
}

ReactDOM.render(html`<${Hello} name="React" />`, document.getElementById("app"));

 

3. .babelrc

 babel-preset-env와 babel-preset-react와 같이 preset을 사용하고 싶으면 root폴더에 .babelrc을 생성하여 사용하고자할 preset을 설정하면 됩니다. plugin들을 각각의 npm dependency를 가지고 있습니다. 하지만 설치시 매번 .bablrc에 설정을 해야하므로 그 두가지를 모두 해결해줄 preset을 사용 하면됩니다. preset을 설치하고 설정하므로서 preset이 가진 plugin들을 설정할 필요없이 사용할 수 있게 됩니다.

 

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

 

4. webpack.config.js

 마지막으로 웹팩 설정파일 입니다. 로더를 이용하여 babel-loader를 적용하고, presets을 추가하여 마무리 하도록 합니다.

 

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

module.exports = {
    entry: "./src/index.js",
    output: {
        path: __dirname + "/dist",
        filename: "index_bundle.js",
    },
    module: {
        rules: [
            {
                test: /\.js$/,
                exclude: /node_module/,
                use: {
                    loader: "babel-loader",
                    options: {
                        presets: ["@babel/preset-env"],
                    },
                },
            },
        ],
    },
    plugins: [new HtmlWebpackPlugin({ template: "./src/index.html" })],
};

 

 

5. 웹팩 생성, 서버 시작

 package.json 에 해당 내용을 추가합니다.

 

 

    "scripts": {
        "start": "webpack-dev-server --mode development --open --hot",
        "build": "webpack --mode production",
        "test": "echo \"Error: no test specified\" && exit 1"
    },

 

 그리고 아래는 웹팩 커맨드입니다..

 

npx webpack

 

 그리고 아래는 웹팩 서버 시작 커맨드입니다.

 

npm start