👟

LaravelとVue.jsで作成したコードを追いかける

2024/04/22に公開

🖌️ この記事を書いたモチベーション

新しく入ったプロジェクトがLaravelとVue.jsを使用したWeb開発だったため
勉強&忘れたときに見返す用に記載。

🐥 読む前に

  • あくまでもフロントエンドエンジニアの視点です
  • 自分がVue.jsを書くためにコードを読むためのものです
    • 前提条件とか知識とか飛ばしているものも多いです

🌏 環境紹介

とはいってもLaravelとVue.jsのバージョンを紹介

  • Laravel 10.42.0
  • Vue.js 2.6.11

👂 まずは画面とコードから

画面のどこのコードが連携しているか分からないと遊んでみることもできない...
ということでURI(画面)とコードの関係性を明らかにしてみる。

ディレクトリ構成の中に routes/ があったのでその配下に記載があると予測、
実際入ってみたらそれっぽいコードが書いてあった。

🗺️ routes/web.php

routes/web.php
// ホーム画面に遷移したときはこんな感じ
Route::get('/', [HomeController::class, 'index']);

// ログインするときはこんな感じ
Route::get('login', [LoginController::class, 'login']);

// nameなるものも付けられるらしい(後述)
Route::get('login', [LoginController::class, 'login'])->name('login');

/ に遷移すると HomeControllerindex 関数に処理が書いてるみたいなので
まずはContollerを見てみて続きのファイルを見てみると計画で進めます。

【補足】 Route::[ここ] について

プロジェクトのコード内では、同じURIに対して

Route::get('login', [LoginController::class, 'login']);
Route::post('login', [LoginController::class, 'login']);

みたいに Route::[ここ] の違う指定がある時があるが、
それはHTTP動詞に対応するものが記載されているらしい。
公式サイト: https://laravel.com/docs/10.x/routing#available-router-methods

HTTP動詞とは??

別名 HTTPリクエストメソッド
※ 英語が「HTTP verb」なので「HTTP述語」と訳されているところも多い

HTTP リクエストメソッドは、ウェブ上の情報を取得したり、送信したりするための方法を示すもの。
GETは情報を取得する、POSTはデータを送信するなどの役割ごとに定義されている
参考: https://developer.mozilla.org/ja/docs/Web/HTTP/Methods

他にもプロジェクトのコードの中に以下の Route:: 関連が存在したのでちょっとだけ調べてみます。

Route::middleware('home')->group(function () {
    Route::get('/', [HomeController::class, 'index']);
});
Route::prefix('home')->group(function () {
    Route::get('/', [HomeController::class, 'index']);
});
Route::name('home')->group(function () {
    Route::get('/', [HomeController::class, 'index'])->name('index');
});
Route::resource('users', UsersController::class)->only(['index', 'create', 'update'])->names('users');
  • Route::middleware はgroupの中に入っているURIにアクセスしたら実行するmiddlewareを記載する
    • 上記のコードだと home というmiddlewareが実行される
    • middlewadreの名前は app/Http/Kernel.php で定義していた
  • Route::prefix は記載のURIに対して共通のprefix(接頭辞)を付ける
    • 上記のコードだとURIが / ではなく /home/ と定義している
  • Route::name はURIではなくnameに対してprefixを付ける
    • 上記のコードだとnameが index ではなく home.index で参照される
  • Route::resource はHTTP動詞の指定なども省略してかけるURI設定方法
    • この対応表 に基づいて判断してくれる
    • 上記のコードだと以下を記載しているのと同義
      • Route::get('users', [UsersController::class, 'index'])->name(users.index);
      • Route::post('users', [UsersController::class, 'create'])->name(users.create);
      • Route::put('users', [UsersController::class, 'update'])->name(users.update);
    • only([ここ]) に入るものは対応表の「Action」にあたるものだけを入れられる

💍 Controller

さっきのホーム画面を例に。

routes/web.php
Route::get('/', [HomeController::class, 'index']);

と記載があったので app/Http/Controllers/HomeController.php を確認して index 関数を見てみる。

app/Http/Controllers/HomeController.php
public function index()
{
    return view('home.index');
}

ということでここでビューというものを呼んでいるんだろうなと推測できました。
画面上で変数を使用したいときは↓みたいな書き方をしてビューを呼ぶときに一緒に渡してあげると使えるみたいです。

app/Http/Controllers/HomeController.php
public function index()
{
   $variable = 'こんな感じで変数を入れてあげる';
    return view('home.index')
        ->with([
            'variable'=> $variable
        ]);
}

🏔️ views

というわけでビューを確認してみましょう。
何となく画面の構成っぽいのでここでvueファイルにありつけると思ったらそんなことはなかったです。
どうやらLaravelには Blade というものがあるらしく、まずはそのファイルを見てみます。
Bladeファイルは resources/views/ 配下にありました。

resources/views/home/index.blade.php
@extends('layouts.layout')

@section('head')
@endsection

@section('title') ホーム画面 @endsection

@section('content')
    <div class="home-container" id="home">
        <home-title :title="Hello, World"></home-title>
    </div>
@endsection

見た所感としてはページのレイアウトを記載する場所という印象。
同時に、 extends という英語から共通レイアウトを :resources/views/layouts/ layout.blade.php で作成されているなということを予測しました。
そして home-title というHTMLタグは存在しないのでvueで作成したコンポーネントだろうとかなーと 🤔。

だいぶ雰囲気が掴めてきたなという気持ちになってきました。

【補足】 name() の効能発揮

先述 routes/web.php で触れていた name() について、Controllerとviewsで結構使用されていたのでここで触れておきます。

nameは簡単にいうとURIの別名定義をしており、遷移指定するときに使います。

routes/web.php
Route::get('/', [HomeController::class, 'index']);
Route::get('login', [LoginController::class, 'login'])->name('login');
Route::name('user')->group(function () {
    Route::get('user', [HomeController::class, 'index'])->name('index');
});

というようなURI指定があったとき、Controllerやviewsで routes() とともに使用できます。
routes('[name]') を入れてあげることでそのnameに定義されたURIへ遷移するという感じです。

app/Http/Controllers/HomeController.php
public function index()
{
    if ([何らかの条件]) {
        return redirect()->route('login')
    }
    return view('home.index');
}
resources/views/home/index.blade.php
@extends('layouts.layout')

@section('head')
@endsection

@section('title') ホーム画面 @endsection

@section('content')
    <a href="{{ route('users.index') }}">ユーザー</a>
@endsection

公式サイト: https://laravel.com/docs/10.x/urls#urls-for-named-routes

🌵 components

先ほど予測した home-title をプロジェクト内で検索してみると resources/js/Home.js が引っかかったので中身を見てみると

resources/js/Home.js
import Vue from 'vue';
import HomeTitle from '../components/HomeTitle.vue';

window.Vue = Vue;

class HomeComponent {
  constructor() {
    const app = new Vue({
      el: '#home',
      components: {
        'home-title': HomeTitle,
      },
    });
    app.$mount('#app');
  }
}

export { HomeComponent, Vue };

が書いてありました。
というわけで home-title と言われていたコンポーネントは resources/components/HomeTitle.vue にあり、
そこでHTMLなりCSSファイルに書いていないスタイルや挙動なりが記載されているみたいです。

つまり、後はこの conponents/ たちを見て色々やってみればOK!

解決! ✨✨✨

とは思ったものの、1つ疑問点が残っていました。
bladeから使用しているコンポーネントはどこで指定しているんだ...??

🪜 JavaScriptの皆様

先ほどの resources/js/Home.jsresources/components/HomeTitle.vueresources/views/home/index.blade.php で使用するよーの指示はJavaScriptファイルたちが活躍してくれていました。

resources/js/app.js に記載があったので見てみると

resources/js/app.js
page('/', () => {
  import(/* webpackChunkName: "home" */ './Home').then(
    ({ HomeComponent }) => {
      return new HomeComponent();
    },
  );
});

というように書いてありました。
つまり / の画面では resources/js/Home.js を読み込んでいるよーとのこと。
さっきのコンポーネントも使用されているよーとのこと。

routes/web.php で定義したURIに対して使いたいVueコンポーネントがあったらここで記載してくれているみたいです。

なので厳密には resources/views/home/index.blade.php ではないのですがそこに該当する画面でのコンポーネントはここで記載しているみたい、なるほど!

解決! ✨✨✨

ということでひとまず追えたかなと!

📰 まとめ

**routes/web.php****画面とController内の関数**の関係性を確認
↓
Controller内の関数で対応している**bladeファイル**を確認
↓
bladeファイルで使用していそうなVueコンポーネントを確認
**resources/js/app.js**から**画面とJavaScriptファイル**の関係性を確認
↓
JavaScriptファイルからVueコンポーネントを確認

の合わせ技で自分が操作したいファイルが分かるはず!

Discussion