コピペコードで快適生活

明日使えるソースを自分のために

React+TypeScript+webpackの環境構築

必要なライブラリのインストール

ビルドツールをインストールする

npm install --save-dev webpack webpack-cli webpack-dev-server typescript ts-loader

React関連のライブラリをインストールする。 ビルド後のファイルに含めるので--saveとする。

npm install --save react react-dom @types/react @types/react-dom
  • react-dom: ReactオブジェクトをDOMに反映するライブラリ
  • @types/react: Reactに関する型定義
  • @types/react-dom: react-domに関する型定義

scriptsの追加

${APP_DIR}/package.jsonにscriptsを追加

{
  "scripts": {
    "build:prod": "webpack --mode production",
    "build": "webpack",
    "watch": "webpack --watch",
    "start": "webpack serve"
  },
  # 略
}

TypeScriptの設定を行う

${APP_DIR}/tsconfig.json に以下を書き出す。

{
  "compilerOptions": {
    "sourceMap": true,
    "target": "ES5",    // ECMAScript 5に変換
    "module": "ES2015", // ES Modulesとして出力
    "jsx": "react",     // JSXの書式を有効に設定

    // 非相対パスを指定したとき、インポート対象をnode_modulesから探す
    "moduleResolution": "node", 

    // targetに含まれていないライブラリを組み込む
    "lib": [
      "ES2020",
      "DOM"
    ]
  }
}

webpackの設定を行う

${APP_DIR}/webpack.config.js に以下を書き出す。

const path = require('path')

module.exports = {
  mode: 'development',

  entry: {
    index: path.join(__dirname, '/src/index.tsx'),
  },

  output: {
    path: path.join(__dirname, 'dist'),
    filename: '[name].js',
  },

  module: {
    rules: [
      {
        test: /\.tsx?$/,          // 拡張子 .ts と .tsx のファイルを
        use: 'ts-loader',         // ts-loaderでトランスパイルする
        exclude: /node_modules/,  // ただし外部ライブラリは除く
      },
    ],
  },

  // 拡張子指定なしでimportできるおまじない
  resolve: {
    extensions: [".ts", ".tsx", ".js", ".json"]
  },

  // ES5向けの指定(webpack 5以上で必要)
  target: ["web", "es5"],

  devServer: {
    host: '0.0.0.0',
    port: 8080,
  },
};

TypeScriptでReactのコードを書いてみる

${APP_DIR}/src/index.tsx

import * as React from "react";
import * as ReactDOM from "react-dom";
import { ShoppingList } from "./ShoppingList";

let element: JSX.Element = <ShoppingList name="weekend"/>;
let dom: HTMLElement = document.getElementById('root');
ReactDOM.render(element, dom);

${APP_DIR}/src/ShoppingList.tsx

import * as React from "react";

interface Props {
  name: string,
};

interface State {
};

export class ShoppingList extends React.Component<Props, State> {
  render() {
    return (
      <div className="shopping-list">
        <h1>Shopping List for {this.props.name}</h1>
        <ul>
          <li>Instagram</li>
          <li>WhatsApp</li>
          <li>Oculus</li>
        </ul>
      </div>
    );
  }
};

${APP_DIR}/index.html

<!DOCTYPE html>
<html>
<head></head>
<body>
  <div id="root"></div>
  <script type="text/javascript" src="./dist/index.js"></script>
</body>
</html>

ビルドなどをする

# ビルド
npm run build

# 開発サーバ立ち上げる
npm run start

補足

いつの間にか、webpackDevServerの起動方法が変わっていた。 webpack-dev-serverwebpack serve

参考