Laravel×Breeze×React×Webpackの環境を構築してみる



# 前提
①LaravelMixは使用しません。なんとなくWebpackの設定を自分でやってみたいからです。
②LaravelとReactとWebpackはある程度知っているという前提で書いていきます。なのでComposerやnpmの使い方やインストールはサラッと流していきます。
③他にワタクシが開発しているLaravelアプリに影響が出るのが怖いのでLaravel9.xは使用しません。使用するのはLaravel8.0です。

# 準備
Composerのインストール
npmのインストール
XAMPPのインストール

Composerのインストールは[こちら](https://getcomposer.org/doc/00-intro.md#installation-windows)
npmは[Nodeの公式ウェブサイト](https://nodejs.org/en/download/)からインストールできます。
XAMPPはYoutubeでインストール方法を説明している動画があります。

# 本編
[1.Laravelのインストール](#1-laravelのインストール)
[2.Breezeのインストール](#2-breezeのインストール)
[3.package.jsonの設定をいじる](#3-packagejsonの設定をいじる)
[4.Reactのインストール](#4-reactのインストール)
[5.Webpackのインストールと設定](#5-webpackのインストールと設定)
[6. Reactのコンポーネントの準備](#6-reactのコンポーネントの準備)
[7. Webpackでindex.jsとimportしているファイルをバンドルする](#7-webpackでindexjsとimportしているファイルをバンドルする)
[8. bandle.jsをwelcome.blade.phpで読み込む](#8-bandlejsをwelcomebladephpで読み込む)
[【おまけ】Q＆A](#おまけqa)


## 1. Laravelのインストール
今回はComposerを使ってインストールしていきます。
まずはLaravel8.0をインストール。
```
composer create-project laravel/laravel:^8.0 [好きなアプリ名]
```
ワタクシは「laravel-breeze-react-app」というネーミングにしました。

## 2. Breezeのインストール
### ①Breezeのインストールの準備
まだLaravelが完全なデフォルトの状態なので、まずはcomposer.jsonにBreezeパッケージを追加します。

:::note info
Breezeパッケージとは
これをインストールすればログイン、ユーザー登録、パスワードのリセット、メールの検証、パスワードの確認など、Laravelのすべての認証機能を追加できる
:::
```
composer require laravel/breeze --dev
```

### ②Breezeのインストール
さっきの作業でcomposer.jsonにBreezeが追加されました。
これでインストールが可能になりましたので、さっそくインストールします。

:::note warn
インストール後に"Please execute the "npm install" && "npm run dev" commands to build your assets."と表示されますが、まだその操作は行わないでください。
npm installをした時に、LaravelMixがインストールされてしまいます。
:::

```
php artisan breeze:install
```
こうして無事にviewsディレクトリやroutesディレクトリに認証機能が作られたファイルが作られました。

## 3. package.jsonの設定をいじる
<b>※LaravelMixを利用したい方はこの章をスキップしてください。</b>
LaravelMixを使いたくないので、package.jsonからLaravelMixを削除しておきます。

```package.json
{
    "private": true,
    "scripts": {
        "dev": "npm run development",
        "development": "cross-env NODE_ENV=development node_modules/webpack/bin/webpack.js --progress --hide-modules --config=node_modules/laravel-mix/setup/webpack.config.js",
        "watch": "npm run development -- --watch",
        "watch-poll": "npm run watch -- --watch-poll",
        "hot": "cross-env NODE_ENV=development node_modules/webpack-dev-server/bin/webpack-dev-server.js --inline --hot --disable-host-check --config=node_modules/laravel-mix/setup/webpack.config.js",
        "prod": "npm run production",
        "production": "cross-env NODE_ENV=production node_modules/webpack/bin/webpack.js --no-progress --hide-modules --config=node_modules/laravel-mix/setup/webpack.config.js"
    },
    "devDependencies": {
        "@tailwindcss/forms": "^0.4.0",
        "alpinejs": "^3.4.2",
        "autoprefixer": "^10.4.2",
        "axios": "^0.19",
        "cross-env": "^7.0",
        "laravel-mix": "^5.0.1",  ←コイツを削除する
        "lodash": "^4.17.19",
        "postcss": "^8.4.6",
        "resolve-url-loader": "^3.1.0",
        "tailwindcss": "^3.0.18"
    }
}
```

これでLaravelMixなしでnpm installができるようになりました。
ではpackage.jsonの中身をインストールしていきます。
```
npm install
```

## 4. Reactのインストール
それではReactをインストールしていきます。
```
npm install --save-dev react react-dom
```
これでpackage.jsonにreactとreact-domが追加されました。
もう一度npm installをしましょう。
```
npm install
```

## 5. Webpackのインストールと設定
Webpackのインストールをします。
ターミナルで下記のコマンドでインストールができます。
```
npm install --save-dev webpack webpack-cli
```

次にWebpackの設定を行っていきます。
### ①Webpack.config.jsを作る
まず、開発ディレクトリ直下（package.jsonと同じディレクトリ）にwebpack.config.jsというファイルを作ります。
そしたらその中にLaravelでReactを使うための設定を書いていきます。
### ②npmでBabelをインストール
WebpackがReactのjsx構文を読み取れるようにします。
以下のコマンドを実行します
```
npm install --save-dev babel-loader @babel/preset-react
```
これでインストールした「babel-loader」と「@babel/preset-react」をWebpackの設定に組み込めば、jsx構文を読み取れるようになり、Reactを使用したjsファイルのバンドルができるようになります。

次でそれらを設定に組み込んでいきます。
### ③Webpack.config.jsの設定
※念のためコメントアウトで各プロパティの説明を書いています。
```webpack.config.js
module.exports = {
    mode: "development",
      //index.jsをエントリーポイントに
    entry: `${__dirname}/resources/js/index.js`,  
      //出力先はpublic内のjsディレクトリに設定（あとでjsディレクトリを作ります）
    output: {
        path: `${__dirname}/public/js`,
        filename: "bandle.js"
    },

    module: {
        rules: [
            // test = loaderを使う特定の拡張子を指定
            // use = testで指定した拡張子にloaderを使いwebpackが読み込めるようにする
            {
                test: /\.js$/,
                use: {
                    loader: 'babel-loader',
                    options: {
                        //↓JSX構文を使ったjsファイルを読み込むためのpresetsを追加する
                        presets: [
                            '@babel/preset-react' //ここにpresetを追加
                        ],
                    }
                },
            },
        ],
    }
}
```
::: note info
    __dirname変数
このファイルが格納されているディレクトリのパスが代入されているグローバル変数らしい。
Node.jsが標準で用意してるらしい？？（コメントで教えてください）
:::

### ④バンドルしたファイルの出力先を作る
先程の設定でバンドル後のjsファイルの出力先をpublic/jsにしたので、publicディレクトリの下にjsディレクトリを作ってください。

以上でWebpackの設定は終わりです。

## 6. Reactのコンポーネントの準備
Reactのindex.jsとコンポーネント（Appコンポーネント）を作っていきます。


### ①index.jsを作る
まずはReactの入り口となるindex.jsを作っていきます。
resources/jsディレクトリ内に作ります。
```resources/js/index.js
import React from 'react';
import ReactDOM from 'react-dom/client';
import App from './app.js';

const root = ReactDOM.createRoot(
  document.getElementById('root')
);
root.render(
  <React.StrictMode>
    <App />
  </React.StrictMode>
);
```

### ②Appコンポーネントを作る
index.jsと同じディレクトリにApp.jsを作ります。
```resources/js/App.js
import React from 'react'

const App = () => {
  return (
    <div>LaravelとReactの連携</div>
  )
}

export default App
```
これでひとまずindex.jsがApp.jsをimportした状態が作れました。

あとはWebpackを動かしてindex.jsとindex.jsがimportしているファイルをバンドルします。

## 7. Webpackでindex.jsとimportしているファイルをバンドルする
以下のコマンドを実行してindex.js達をバンドルしていきましょう。
```
npx webpack
```
successfullyと表示されたらpublicディレクトリを見てください。
bandle.jsファイルが作られていたら成功です。

## 8. bandle.jsをwelcome.blade.phpで読み込む
最後にそのファイルをwelcome.blade.phpで読み込んでいきましょう。
welcome.blade.phpの中身を全て消して、以下をコピペしましょう。
```welcome.php
// ↑ Qiitaの仕様上、タイトルがwelcome.phpになってますが本来はwelcome.blade.phpです。

<!DOCTYPE html>
<html lang="{{ str_replace('_', '-', app()->getLocale()) }}">
    <head>
        <meta charset="utf-8">
        <meta name="viewport" content="width=device-width, initial-scale=1">

        <title>Laravel</title>
    </head>
    <body>
        <div id="root"></div>
    </body>
    <script src="js/bandle.js"></script>
</html>
```
php artisan serveをして開いてみましょう。
![1654289874476.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1311883/40835791-07d8-05d4-118b-781cba577314.jpeg)

Laravell×Breeze×React×Webpackの環境の完成です！！
気が向けばInertia.jsやFetch APIを用いたLaravelとReactの通信を記事にしようかなーなんて思ってます。
とりあえずReactやLaravel系の記事を書いていく予定です！
その時はまた閲覧ヨロシクお願いします。

## 【おまけ】Q＆A
:::note warn
Ｑ．Webpackでバンドルしなくてもindex.jsをwelcome.blade.phpから引っ張れば使えるんちゃうか？？

Ａ．resourcesにあるindex.jsは直接呼び出せません。
Laravelはpublicディレクトリ(以下public)にあるファイルを出力しているのでresourcesディレクトリにあるindex.jsは使えません。
resourcesディレクトリにあるindex.jsとそれがimportしているファイル（React,ReactDOM,App.js）をまとめてバンドルしたbundle.jsをpublic内に配置することで、それらがpublicから使えるようになるってワケ

（なおワタクシの推測です）
:::
:::note warn
Ｑ．npx webpackでエラーが出た

Ａ．ワンチャンわたしの記事で救えます。
[【React】Webpackの設定で3種類のエラーが出たから原因と解決方法をここに記す](https://qiita.com/yowatsuyoengineer/items/ada5358b9e50395eb857)
:::