Webpack-React-Typescriptボイラープレート
どいつもこいつもcreate-react-appしやがって...
実際のところcreate-react-appを叩いて0からReactアプリを作る機会があんまりないので、最小構成を作っておいて、応用する形で使えるようにしておく備忘録です。
- node 12.2.0
- webpack 4.43.0
- react 16.13.1
- typescript 3.9.5
webpack, react, typescriptをそれぞれインストールします。 typescriptでreactを扱うので型定義とtypescriptをwebpackでパッキングするためのts-loaderも必要です。
npm install --save-dev webpack webpack-cli
npm install --save-dev typescript
npm install --save-dev ts-loader
npm install react react-dom @types/react @types/react-dom
package.jsonのscriptsでbuildとwatchを叩けるようにしておきます。
{
...
"scripts": {
"build": "webpack",
"watch": "webpack -w"
},
...
}
webpack.config.jsを書きます。
webpack-scaffoldってのもありますが、これを使うのはcreate-react-app使うのと本質的に同じなので、手動で書きます。
module.exports = {
mode: "development",
entry: "./src/index.tsx",
output: {
path: `${__dirname}/dist`,
filename: "index.js"
},
module: {
rules: [
{
test: /\.tsx?$/,
use: "ts-loader"
}
]
},
resolve: {
extensions: [".ts", ".tsx", ".js", ".jsx"]
}
};
tsconfig.jsonを作成します。
npx tsc --init
tsconfig.jsonのcompilerOptions.jsxをreactに指定してjsx内のReact構文を解釈できるようにしておきます。
{
"compilerOptions":{
...
"jsx": "react",
...
}
}
あとは適当にtsxを書くとnpm run buildでビルド可能です。
import { Component } from "react";
import React from "react";
import ReactDOM from "react-dom";
class Index extends Component{
public render(): JSX.Element{
return(
<div>Hello !!</div>
);
}
}
const app = document.createElement('div');
document.body.appendChild(app);
ReactDOM.render(<Index />, app);
+マルチページアプリケーション
ReactといえばSPAみたいなところありますが、わりとマルチページなReactアプリを構築する機会が多いので、マルチページ用のボイラープレートも追加しておきます。
webpackでhtmlをバンドルする必要があるので、html-webpack-pluginとhtml-loaderをインストールします。
npm install --save-dev html-webpack-plugin html-loader
エントリポイントに対応するhtmlを出力するようにwebpack.config.jsを書き換えます。
const HtmlWebpackPlugin = require('html-webpack-plugin');
module.exports = {
mode: "development",
entry:{
"index": "./src/index.tsx",
"page1": "./src/page1.tsx",
},
output: {
path: `${__dirname}/dist`,
filename: "[name].js"
},
module: {
rules: [
{
test: /\.tsx?$/,
use: "ts-loader"
},
{
test: /\.html$/,
loader: "html-loader"
}
]
},
plugins:[
new HtmlWebpackPlugin({
chunks: ["index"],
filename: "index.html",
}),
new HtmlWebpackPlugin({
chunks: ["page1"],
filename: "page1.html",
}),
],
resolve: {
extensions: [".ts", ".tsx", ".js", ".jsx"]
}
};
ページが増えるたびに2箇所変更箇所があるのが嫌なところですね。
いい方法を知っていたら教えてください。