参考サイト:https://laracasts.com/discuss/channels/livewire/app-debug-to-false-causes-a-404-error-on-livewirejs
【これを書くに至った経緯】
ローカル環境では問題なくLivewireが動作していたのに、リモートサーバーへLaravelプロジェクトをデプロイした際、ブラウザで以下のエラーが発生しました。
failed to load resource: the server responded with a status of 404 ()
Livewire.jsが https://XXXX.com/livewire/livewire.min.js?id を探しに行き、404エラーが発生。
.envファイルの APP_DEBUGをtrue にすると問題なく動作するものの、false にすると正常に動作しなくなりました。
【結論から言うと】
php artisan livewire:publish --assets
コマンドを実行し、Livewireのアセットをpublicディレクトリに公開することで解決しました。
【なぜAPP_DEBUGがtrueだと動作するのに、falseだと動作しないか】
APP_DEBUGの設定によって、Laravelの動作が次のように変化します。
APP_DEBUG=true
- Laravelは デバッグモード で動作し、Livewireの 動的アセット生成機能 が有効になります。
- https://XXXX.com/livewire/livewire.min.js のリクエストがあれば、Laravelアプリケーションが自動的にJavaScriptを生成して提供します。
- このため、public/livewire/livewire.min.jsファイルが存在しなくても問題なく動作します。
APP_DEBUG=false
- APP_DEBUG=false に設定すると、Laravelは 本番環境を前提とした動作モード に切り替わります。
- もしpublic/livewire/livewire.min.jsが存在しない場合、サーバーは404エラーを返します。
- 本番モードでは動的アセット提供が無効化されるため、アセットファイルを公開する必要があります。
【なぜpublic内にlivewireのアセットを公開する方法で解決するのか】
本番では、Laravelは静的アセットを直接提供することを期待します。
php artisan livewire:publish --assets により、必要なアセットが正しい場所に配置され、Laravelやサーバーが適切にレスポンスを返せるようになります。
php artisan livewire:publish --assets
コマンドを実行すると、Livewireが必要とするJavaScriptファイルが public/livewireディレクトリに配置されます。
生成されるファイル
public/
└── livewire/
├── livewire.js
├── livewire.min.js
└── livewire.js.map
問題解決の流れ
①ブラウザが https://XXXX.com/livewire/livewire.min.js をリクエスト。
②サーバーが public/livewire/livewire.min.js を返却。
③必要なアセットが正しい場所に配置されているため、404エラーが解消。
【なぜローカル環境ではAPP_DEBUGがfalseでも動作していたのか】
①Laravelの内部ルーティングがリクエストを動的に処理していた。
②PHPビルトインサーバーの柔軟な動作により、静的アセットがなくても正常に処理されていた。
③開発環境特有のキャッシュや動的アセット生成が影響していた。
上記などが考えられます。本番環境では、これらの柔軟性がなくなるため、public/livewire/livewire.js などの静的アセットを明示的に配置する必要があるようです。
【まとめ】
問題の原因:
APP_DEBUG=false では、Laravelは動的アセット提供を行わず、静的アセット(public/livewire/livewire.min.js)が必要になる。(今回のパターンではpublic/vendor/livewire/livewire.min.js)
解決方法:
php artisan livewire:publish --assets を実行して、必要なアセットを公開する。
ポイント:
ローカル環境で動作しても、本番環境では静的アセットが必須であるため、適切に公開することが重要。