[Laravel11+LIVEWIRE #1]とりあえず試してみる(Installation)

Laravel
LIVEWIRE LOGO

LaravelでReactやVueも使えるけど、公式によるとLIVEWIREの相性がいいとか。読み方はたぶん「らいぶわいやー」だと思う。どうもLIVEWERE(らいぶうぇあ)って書いてしまう…
とりあえずやってみる。基本的には公式のインストール手順に従いつつ、最小限での動作を目指す!

参考)https://livewire.laravel.com/

まずはさくっとLaravelプロジェクト作成

プロジェクト作成

% composer create-project laravel/laravel livewire_study

XAMPPのhtdocsにシンボリックリンクを作成&パーミッション変更

% cd /Applications/XAMPP/htdocs
% ln -s /Users/shimo/workspace/livewire_study/public livewire_study
% sudo chmod -R 777 storage/

.envファイルを修正

#SESSION_DRIVER=database
SESSION_DRIVER=file

ブラウザで表示すると初期画面が表示される。

LIVEWIREをインストール

Composerで一発完了!

composer require livewire/livewire

サンプル画面を作っていく

職人さん(artisan)で初期ファイルを作る。

% php artisan make:livewire counter
 COMPONENT CREATED  🤙

CLASS: app/Livewire/Counter.php
VIEW:  resources/views/livewire/counter.blade.php

  _._
/ /o\ \   || ()                ()  __
|_\ /_|   || || \\// /_\ \\ // || |~~ /_\
 |`|`|    || ||  \/  \\_  \^/  || ||  \\_


Congratulations, you've created your first Livewire component! 🎉🎉🎉

メッセージにある通り、クラスファイルとビューファイルが生成されるので、編集する。

app/Livewire/Counter.php

<?php
 
namespace App\Livewire;
 
use Livewire\Component;
 
class Counter extends Component
{
    public $count = 1;
 
    public function increment()
    {
        $this->count++;
    }
 
    public function decrement()
    {
        $this->count--;
    }
 
    public function render()
    {
        return view('livewire.counter');
    }
}

resources/views/livewire/counter.blade.php

<div>
    <h1>{{ $count }}</h1>
 
    <button wire:click="increment">+</button>
 
    <button wire:click="decrement">-</button>
</div>

routes/web.php

use App\Livewire\Counter;
 
Route::get('/counter', Counter::class);

職人さんにレイアウトファイルを作ってもらう。

% php artisan livewire:layout
 LAYOUT CREATED  🤙

CLASS: resources/views/components/layouts/app.blade.php

resources/views/components/layouts/app.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.0">

        <title>{{ $title ?? 'Page Title' }}</title>
    </head>
    <body>
        {{ $slot }}
    </body>
</html>

ブラウザでhttp://localhost/livewire_study/counterに接続すると、以下の内容が表示される。

動作させてみる

プラスボタンやマイナスボタンを押すとカウンターが増減するのかと思いきや動かない…
ブラウザのコンソールを見ると…

そりゃそうだ。そんなパス作ってないもの。 調べてたら公式に回答がありました。

デフォルトでは、Livewire はアプリケーション内でルートを公開し、/livewire/livewire.js から JavaScript アセットを提供します。ほとんどのアプリケーションではこれで問題ありませんが、カスタム構成の Nginx を使用している場合は、このエンドポイントから 404 を受け取ることがあります。この問題を解決するには、Livewire の JavaScript アセットを自分でコンパイルするか、これを許可するように Nginx を構成します。

そもそもlivewire.jsってあるのかと思い、`http://localhost/livewire_study/livewire/livewire.js`にブラウザで見てみるとあるじゃないか!

ってことは、パスを設定してあげれば良いってことだよね!

routes/web.php

以下を追加(このファイルでいいのか?サービスプロバイダがいいのか?)

Livewire::setUpdateRoute(function ($handle) {
    return Route::post('/livewire_study/livewire/update', $handle);
});
Livewire::setScriptRoute(function ($handle) {
    return Route::get('/livewire_study/livewire/livewire.js', $handle);
});

画面をリロードするとjsの読み込みエラーはなくなっているので、ドキドキしながらプラスボタンを押すと、動いた!!

ルートの設定で、liveware_studyって直接書くのは嫌なんだよねぇ…開発環境によって変わるし。
まずはsetScriptRouteを以下のように変えると問題なく動作する。開発環境によって縛られることはない。

Livewire::setScriptRoute(function ($handle) {
    //return Route::get('/livewire_study/livewire/livewire.js', $handle);
    return Route::get(url('/livewire/livewire.js'), $handle);
});

同じようにsetUpdateRouteも以下のように変更してみる。

Livewire::setUpdateRoute(function ($handle) {
    return Route::post(url('/livewire/update'), $handle);
});

これで動かすと、通信するURLは「http://localhost/http://localhost/livewire_study/livewire/update」…

なんでやねん!http://localhost/を先頭に付与するんかい!ってことでいろいろと調べたけどいい感じのロジックがない…仕方がないので、.envに以下を追加。

LIVEWIRE_UPDATE_PATH=livewire_study/livewire/update

んで、setUpdateRouteは以下のように変更。

Livewire::setUpdateRoute(function ($handle) {
    return Route::post(env('LIVEWIRE_UPDATE_PATH'), $handle);
});

これで動作する。あんまり好きなやり方じゃないけど仕方ない。

感想

Reactはnpmとか常駐させないとダメだけど、こいつはいい感じだ!

次回はコンポーネントを学ぶ↓↓↓

[Laravel11+LIVEWIRE #2]コンポーネント(Components)

コメント

タイトルとURLをコピーしました