Laravel と Vue を連携する方法

こんにちは❗フリーランス・エンジニアの 九保すこひ です。

さてさて、このブログでは長らくLaravelVueについて記事を公開してきました。

どちらも「シンプルなのに高機能」という点が人気の理由だと思うのですが、そんな両者は、ときに「連携」してデータを渡す必要が出てきます。

例えば、LaravelでDBからデータを取得してVueで表示するような場合です。

そして、そんな連携をする場合、少しテクニックが必要になったりします。

そこで❗

今回は、LaravelVueを連携させる方法をまとめてみることにしました。
ぜひ皆さんの学習に役に立ちましたら嬉しいです😊✨

「レトルトのパスタソースが
こんなにウマいとは❗」

開発環境: Laravel 8、Vue 3

直接 Vue のコードに埋め込む場合

Laravelのテンプレート・エンジン「Blade」を使って、Vueにデータを渡します。

おおまかに言うと、コントローラーで次のようにビューを呼び出してします。

// 省略

class HomeController extends Controller
{
    public function laravel_vue_cooperation() {

        return view('laravel_vue_cooperation')->with([
            'string' => '文字列',
            'number' => 1,
            'boolean' => true,
            'array' => ['太郎', '次郎', '三郎'],
            'collection' => collect([
                '太郎',
                '次郎',
                '三郎'
            ]),
            'null' => null,
            'model1' => User::find(1),
            'model2' => User::select('name')->take(3)->get()
        ]);

    }

// 省略

そして、データを以下のようにセットすることになります。

<!-- Bladeファイルの中です -->

<script>

    Vue.createApp({
        data() {
            return {
                
                // JavaScript内にデータを埋め込む

            }
        }
    }).mount('#app');

</script>

では、各データタイプの埋め込み方をひとつずつ見ていきましょう❗

文字列

文字列の埋め込みは、連携の基本になります。

data() {
    return {
        string: '{{ $string }}' // 👈 ここ
    }
}

ここでまず重要なのが{{}}で囲まれた部分です。

この部分はBladePHPの変数と入れ替えてくれますので、今回の例で言うと「文字列」に入れ替わります。

そして、次に{{ $string }}がシングルクォートで囲まれている部分も重要です。

なぜなら、$stringが「文字列」に入れ替わった後のことを考えないといけないからです。

つまり、このシングルクォートはJavaScriptのために書いています。
では、実際に実行後のコードを見てみましょう。

data() {
    return {
        string: '文字列',
    }
}

このようにシングルクォートが表示され、うまくJavaScript側と連携していますね。

もしシングルクォートを書かない場合、以下のようになりエラーが発生することになります。

data() {
    return {
        string: 文字列, // ⚠ これはエラーになります。
    }
}

ちなみに、Bladeの{{ ... }}を使えば、以下のように初期値をつくることもできるので便利ですよ👍

data() {
    return {
        string: '{{ $string ?? '初期値' }}'
    }
}

この例の場合、$stringが存在しない場合、自動的に初期値が表示されることになります。

※「存在しない場合」というのはnullの場合です。空白の場合はそのまま表示されるので注意してください。

data() {
    return {
        string: '初期値' // 👈 初期値が採用されます
    }
}

数値の場合

数値の場合もほぼ文字列のときと同じです。

data() {
    return {
        number: {{ $number }}
    }
}

ただし、厳密に「数値」としてデータを渡す場合、文字列のようにシングルクォートで囲んではいけません。

なぜなら、シングルクォートで囲んでしまうと、実行後のコードは以下のようになってしまうからです。

data() {
    return {
        number: '1' // 👈 これは「文字列」として扱われます
    }
}

なお、IDEやテキストエディタによっては、

number: {{ $number }}

と書いてしまうと、JavaScriptのコードとしては間違っているのでエラーがでる場合があります。

もしそれが気になる場合は以下のようにするといいでしょう。

data() {
    return {
        number1: parseInt('{{ $number }}'), // 👈 int型の場合
        number2: parseFloat('{{ $number }}'), // 👈 float型の場合
    }
}

これでエラーはでなくなりますし、変数の中身を明確にしているので、よりエラーが発生しにくくなるでしょう。(parseIntparseFloatは型を変換するJavaScriptの関数です)

Boolean(true or false)の場合

Boolean型を埋め込む場合は少し注意が必要です。

なぜなら、ここまででみてきたように埋め込んでしまうとtruefalseではなく数値になってしまうからです。

data() {
    return {
        boolean: {{ $boolean }} // 👈 「1」になる
    }
}

そのため、明確にBooleanとして埋め込むには次のようにします。

data() {
    return {
        // 👇 PHPの分岐を使う
        boolean: {{ ($boolean) ? 'true' : 'false' }}
    }
}

配列

配列を埋め込む場合は、以下のようにします。

data() {
    return {
        array: @json($array) // 👈 JSONにしてくれる
    }
}

ただし、@jsonLaravel 5.5以降で使える書き方ですので、それ以外の場合は、json_encode()を使ってください。

data() {
    return {
        array: {!! json_encode($array) !!} // 配列をJSONへ変換
    }
}

なお、お気づきの方もいらっしゃるかと思いますが、json_encode()を使う場合、{!!!!}で囲んでいます。

なぜなら、通常どおり{{ ... }}を使ってしまうと、ダブルクォートがエスケープされてしまい、JavaScriptのコードとしてエラーになってしまうからです。

実際の例を見てみましょう。
まずは、{!!!!}で囲んだ正しい結果です。

data() {
    return {
        // 正しくダブルクォートで囲まれています 👍
        array: ["\u592a\u90ce","\u6b21\u90ce","\u4e09\u90ce"]
    }
}

次に間違った例です。(エラーになります)

// ⚠ これは間違った例です。

data() {
    return {
        // ダブルクォートがエスケープされて「&quot;」になっています...😫
        array: [&quot;\u592a\u90ce&quot;,&quot;\u6b21\u90ce&quot;,&quot;\u4e09\u90ce&quot;]
    }
}

コレクション、モデル

コレクションやモデルの場合も配列とほぼ同じように埋め込むことができます。

data() {
    return {
        collection: @json($collection)
    }
}

なお、Laravel 5.4以下の場合は次のようにしてください。

data() {
    return {
        collection: {!! $collection !!}
    }
}

※ 実は、Laravelのコレクション・モデルはjson_encode()を使わなくても自動でJSON化してくれるんですね👍

元も子もない話

なお、実は元も子もない話があって、なんと、どんなデータタイプの値であっても@jsonに入れてあげればうまくいくんですね。

こんなカンジです。

data() {
    return {
        string: @json($string),
        number: @json($number),
        boolean: @json($boolean),
        array: @json($array),
        collection: @json($collection)
    }
}

ただし、全てに@jsonを使ってしまうと、変数の中身が分かりにくくなりますし、IDEの方でJavaScriptのエラーがでるので、個人的にはこれまで紹介した個別の書き方をしています。(この辺は好みもあるかもしれません😊)

Ajaxを使う場合

LaravelVueを連携させるもうひとつの方法が、Ajaxでデータを取得しVueへセットするという方法です。

では、実際の方法を順を追ってみていきましょう。(なお、Ajax通信にはaxiosを使います)

Laravelでデータ部分をつくる

まずは、LaravelJSONデータを提供する部分をつくります。

ルートをつくる

では、ルートです。

routes/web.php

Route::get('json_data', [HomeController::class, 'json_data'])->name('json_data');

※ なお、メソッドをGETにしていますが、Ajaxでパラメータと一緒に送信する場合はPOSTの方がいいかもしれません。

通常通りの書き方ですが、name()で「json_data」という名前をつけていることを覚えておいてください。後ほどVue側で使います。

コントローラーをつくる

続いてコントローラーです。
まずは以下のコマンドでHomeControllerをつくります。

php artisan make:controller HomeController

すると、ファイルが作成されますので、中身を以下のように変更してください。

app/Http/Controllers/HomeController.php

<?php

namespace App\Http\Controllers;

// 省略

class HomeController extends Controller
{
    public function json_data() {

        $string = '文字列';
        $number = 12345;
        $boolean = true;
        $array = ['太郎', '次郎', '三郎'];
        $object = [
            'key_1' => 'value_1',
            'key_2' => 'value_2',
            'key_3' => 'value_3',
        ];

        return [
            'string' => $string,
            'number' => $number,
            'boolean' => $boolean,
            'array' => $array,
            'object' => $object
        ];

    }

    // 省略

この中では、以下のタイプのデータをそれぞれ配列にしてreturnしています。

  • 文字列
  • 数値
  • 真偽値(Boolean)
  • 配列
  • オブジェクト ※

※PHPの場合「連想配列」と呼んだほうがいいでしょうが、今回はJavaScript側に合わせて「オブジェクト」と呼びます。

ちなみに、LaravelJSONのデータを返したい場合は、わざわざビューを作らなくてもコントローラーから値をreturnするだけでOKです👍

では、実際の表示を見てみましょう。

うまくJSONデータが表示できています😊

Vueでデータ取得して変数へセットする部分をつくる

では、Vue側から先ほど作ったJSONデータを取得し、変数へセットする部分をつくっていきましょう。

以下のようなビューをつくってください。(重複するので、ルートとコントローラーは省略しますがお好みで作ってください)

<html>
<head>
    <link rel="stylesheet" href="https://stackpath.bootstrapcdn.com/bootstrap/4.5.0/css/bootstrap.min.css">
</head>
<body>
<div id="app">
    <!-- ③ 変数の中身を表示 -->
    <span v-text="string"></span>
    <span v-text="number"></span>
    <span v-text="boolean"></span>
    <span v-text="array"></span>
    <span v-text="object"></span>
</div>
<script src="https://code.jquery.com/jquery-3.5.1.min.js"></script>
<script src="https://stackpath.bootstrapcdn.com/bootstrap/4.5.0/js/bootstrap.min.js"></script>
<script src="https://unpkg.com/vue@3.0.2/dist/vue.global.prod.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/axios/0.19.2/axios.min.js"></script>
<script>

    Vue.createApp({
        data() {
            return {
                string: '',
                number: 0,
                boolean: false,
                array: [],
                object: {}
            }
        },
        methods: {
            getJsonData() { // ② AjaxでJSONを取得

                const url = '{{ route('json_data') }}'; // ここでもLaravelと連携
                axios.get(url)
                    .then(response => {

                        this.string = response.data.string;
                        this.number = response.data.number;
                        this.boolean = response.data.boolean;
                        this.array = response.data.array;
                        this.object = response.data.object;

                    });

            }
        },
        mounted() {

            this.getJsonData(); // ① データ取得メソッドを実行

        }
    }).mount('#app');

</script>
</body>
</html>

では、順を追ってみていきましょう。

① データ取得メソッドを実行

mounted()はページが表示されたらすぐに実行されますので、ここでJSONデータ取得用のgetJsonData()を呼んでいます。

② AjaxでJSONを取得

axiosを使ってLaravel側に作ったJSONデータを取得する部分です。

ここで注意していただいきたいのが、URLLaravelのヘルパー関数route()で取得している部分です。こうすることによって、もし今後ルートのURLが変更になってもこのコードは変更しなくて済むようになります。

そして、axiosの場合、通信が成功するとresponse.dataからデータを取得できますので、それぞれのデータをVueの変数へセットしています。

③ 変数の中身を表示

ここはVue変数の中身を確認するためにつくりました。

Ajax通信が早い場合はあまりわかりませんが、以下の順序で変化します。

  1. はじめは何も表示されていない
  2. 変数がセットされると中身が表示になる

おまけ:BladeでVueの変数を表示する場合

ご存知のとおり、BladePHPの変数を表示する場合は、{{}}で囲むことになっています。

<span>
    <!-- 変数と入れ替わる -->
    {{ $value }}
</span>

しかし、Vueの場合はどうでしょうか。
そうです。同じく{{}}で囲むことになっています。

そのため、Bladeの中でVueを使う場合、気をつけないとエラーが発生してしまいます。

では、どのようにすればVueのために{{}}を用意することができるでしょうか。答えは、「」です。

以下のように先頭に@をつけると、そのまま表示することができるんですね。

<span>
    <!-- ここはそのまま表示されます -->
    @{{ javaScriptValue }}
</span>

つまり、実行すると以下のようになります。

<span>
    {{ javaScriptValue }}
</span>

なお、個人的には混同しなくてすむので、v-textを使うことが多いです👍

<!-- 上と同じ結果になります。 -->
<span v-text="javaScriptValue"></span>

おわりに

ということで、今回はPHPJavaScript界で人気のパッケージLaravelVueを連携させてみました。

実際の開発では、サーバーサイトとクライアントサイドは緊密に連携をすることが多いと思いますので、今回のサンプルでおおまかな雰囲気を感じていただけると嬉しいです。

後は、同じデータを複数回使う、また、パラメータで内容を可変にする場合はAjaxでデータ取得すると後々の開発も楽になると思います。

ぜひ皆さんもやってみてくださいね。

ではでは〜❗

「空気清浄機ってこんなに
いいもんだったとは❗」

開発のご依頼お待ちしております 😊✨ お問い合わせ
また、こちらもお待ちしております。
  • 実案件の開発サポート: 詳細
  • ツイッターのフォロー: 詳細
どうぞよろしくお願いいたします!
このエントリーをはてなブックマークに追加       follow us in feedly