Laravel から JavaScript へ 変数 を渡す方法一覧

Laravelを使っていて、偶にJavaScript側へ変数を渡したい場面に遭遇します。
手法がいろいろあり、毎回忘れるので一覧化して残しておきたいと思います。

#Bladeファイル内にJavascriptを記述して渡す
多分一番簡単な方法。

文字列と配列をそれぞれ渡した場合のサンプル

```HTML:hoge.blade.php
<!doctype html>
<html>
<head>
</head>
<body>
なんらかの記述
<script>
const name = @json($name);
console.log(name);
//これでも
const name2 = '{{$name}}';

const array = @json($array);
console.log(array)


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

```

```
>name

>(5) [{…}, {…}, {…}, {…}, {…}]
0: {id: 1, name: "yamada"}
1: {id: 2, name: "yoshida"}
2: {id: 3, name: "sato"}
3: {id: 4, name: "kimura"}
4: {id: 5, name: "hoge"}
length: 5
__proto__: Array(0)

```

#ライブラリ Transform PHP Vars to JavaScript を使う
Transform PHP Vars to JavaScriptを使うと簡単にJS側に変数を渡すことができるようです。
詳しくは[公式](https://github.com/laracasts/PHP-Vars-To-Js-Transformer)を参照してください

以下、手順の抜粋

>多くの場合、JavaScriptにサーバー側の文字列/配列/コレクション/いろいろ渡したい状況に陥ります。
特にアプリが大きくなると、これは少し大変になる場合があります。

##インストール

```
composer require laracasts/utilities:~2.0
```
※Laravel 4：を使用する場合、~1.0にこのパッケージをインストールします
※Laravel 5（または非Laravel）の場合~2.0を使用します

##サービスプロバイダに登録(Laravel5.5以降は不要)

```php:app.php
// config/app.php

'providers' => [
    '...',
    'Laracasts\Utilities\JavaScript\JavaScriptServiceProvider'
];

```

##デフォルト構成を公開

```
php artisan vendor:publish --provider="Laracasts\Utilities\JavaScript\JavaScriptServiceProvider"
```
##使う
```php

public function index()
{
    JavaScript::put([
        'foo' => 'bar',
        'user' => User::first(),
        'age' => 29
    ]);

    return View::make('hello');
}
```

```
console.log(foo); // bar
console.log(user); // User Obj
console.log(age); // 29
```
footerのビューでバインドしているとのことなので、変えたい場合は`config/javascript.php`をいじるとのこと

#グローバル定義して、別ファイルで扱う
```HTML:hoge.blade.php
<!doctype html>
<html>
<head>
</head>
<body>
なんらかの記述
<script>
//名前衝突が起こらないように、Laravelをつけています

window.Laravel = {};
window.Laravel.name = @json($name);
window.Laravel.array = @json($array);

</script>
<script src="{{ asset('js/hoge.js') }}"></script>
</body>
</html>

```
別ファイルのjsで呼び出す。
グローバル定義していないページで呼び出そうとしたら当然エラーとなります。
やっていることは、実質上のライブラリと同じ。(だと思う。)
VueなどのSPAで使われているのはたまに記事で見かけます。

```js:hoge.js
console.log(Laravel.name);
console.log(Laravel.array);
```
```
>name

>(5) [{…}, {…}, {…}, {…}, {…}]
0: {id: 1, name: "yamada"}
1: {id: 2, name: "yoshida"}
2: {id: 3, name: "sato"}
3: {id: 4, name: "kimura"}
4: {id: 5, name: "hoge"}
length: 5
__proto__: Array(0)

```
#HTMLのどこかに一度挿入後、取得
data属性なりに渡したい変数を格納してやり、jsで取得してやる。

```HTML:hoge.blade.php
<span id="js-getVariable" data-name="{{ $name }}"></span>
```

```js:hoge.js
const name = $('#js-getVariable').data();
console.log(name);//yamada
```

#API化して、取得する
変数を受け渡すの定義内に入るかはわかりませんが、
アプリケーションがLaravel内で完結するなら`web.php`に
外部アプリから使用するなら`api.php`に適当にレスポンスを返却するルーティングを作成し
jqueryなら`ajax`、vueなら`axios`で等の非同期通信で取得してやる。

```php

Route::get('data'function(){
    return response()->json(['name' => 'yamada']);
});

```

```js:hoge.js
$(function ()
{
    let LaravelData = null;
    $.ajax({
        url: './data',
        type: 'get',
    })
    .then(// 1つめは通信成功時のコールバック
    function (data) {
        LaravelData = data.name;
    },
    function () {
        console.error("読み込み失敗");
    });

});
```


#まとめ
こんなところでしょうか。
外部ファイルのJSで使いたかったら、非同期で取得、場合によってはdata属性
Blade内に書いて問題ないなら、Blade内で処理するのがいいのでは...と思っています。

間違いや、別な手法、より良い方法が御座いましたら、ご指摘お願いいたします。

----
ブログ始めました

https://collapse-natsu.com/