【Laravel 5.8対応】掲示板を作成するチュートリアル

Laravel初心者の方向けに、掲示板のチュートリアルを作成しました。
このチュートリアルを通じて、基本的なCRUD処理を中心に、

  • ルーティング
  • コントローラー
  • バリデーション
  • EloquentORM
  • ページネーション
  • withメソッドを利用してクエリのチューニング

について簡単に触れて、これからLaravelを始めるための最初の一歩になればと思います。

チュートリアルで作成する掲示板のデモはこちらにアップしています。ご自由に触ってください。

仕様の概要

これから作成する掲示板について、仕様についてざっくりまとめます。

データベース

Laravel 掲示板 ER図

投稿とコメントテーブルを作成して、投稿は複数のコメントを持てるようにします。

URL

URLはこちらのようにします。

メソッドURL説明
GET,HEAD/トップページ。投稿の一覧を表示する。
POSTposts投稿を追加する。
GET,HEADposts/create投稿の作成ページを表示する。
GET,HEADposts/{post}投稿の詳細を表示する。
PUT,PATCHposts/{post}投稿を編集する。
DELETEposts/{post}投稿を削除する。
GET,HEADposts/{post}/edit投稿の編集ページを表示する。
POSTcomments投稿にコメントを追加する。

Laravelアプリケーションを作成する

まず最初に、下記のコマンドを実行してアプリケーションを作成しましょう。

$ laravel new laravel-bbs

初期設定

次に、アプリケーションの初期設定を行います。

ENVファイルの設定

.envファイルを編集して初期設定を行います。
今回はメールなどは利用しませんので、データベースの設定を自分のローカル用に設定しましょう。
※ 以下はmampを利用した場合の設定例です。

DB_CONNECTION=mysql
DB_HOST=localhost
DB_DATABASE=laravel_bbs
DB_USERNAME=root
DB_PASSWORD=root
DB_SOCKET=/Applications/MAMP/tmp/mysql/mysql.sock

日本語環境の設定

タイムゾーンを日本、言語を日本に設定します。
config/app.phpファイルを編集して下記の項目について変更します。

'timezone' => 'Asia/Tokyo',

'locale' => 'ja',

データベースの作成

データベースのテーブルを作成するためのマイグレーションファイルを作成します。
※ データベース(ここでは、「laravel_bbs」という名前)は事前に作成しておく必要があります。

雛形にユーザー用のマイグレーションが含まれていますが、今回は利用しませんので下記のファイルは削除しておきます。

  • 2014_10_12_000000_create_users_table.php
  • 2014_10_12_100000_create_password_resets_table.php

posts, commentsテーブルを作成します。下記のコマンドを実行しましょう。

$ php artisan make:migration create_posts_table --create=posts
$ php artisan make:migration create_comments_table --create=comments

○○_create_posts_table.php○○_create_comments_table.phpが作成されました。
マイグレーションの実行順序をつけるため、ファイル名にマイグレーションファイルの作成日時がついています。

○○_create_posts_table.phpを下記のように編集します。

<?php

use Illuminate\Support\Facades\Schema;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Database\Migrations\Migration;

class CreatePostsTable extends Migration
{
    /**
     * Run the migrations.
     *
     * @return void
     */
    public function up()
    {
        Schema::create('posts', function (Blueprint $table) {
            $table->increments('id');
            $table->string('title', 50);
            $table->text('body');
            $table->timestamps();
        });
    }

    /**
     * Reverse the migrations.
     *
     * @return void
     */
    public function down()
    {
        Schema::dropIfExists('posts');
    }
}

続いて、○○_create_comments_table.phpを下記のように編集します。

<?php

use Illuminate\Support\Facades\Schema;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Database\Migrations\Migration;

class CreateCommentsTable extends Migration
{
    /**
     * Run the migrations.
     *
     * @return void
     */
    public function up()
    {
        Schema::create('comments', function (Blueprint $table) {
            $table->increments('id');
            $table->unsignedInteger('post_id');
            $table->text('body');
            $table->timestamps();

            $table->foreign('post_id')->references('id')->on('posts');
        });
    }

    /**
     * Reverse the migrations.
     *
     * @return void
     */
    public function down()
    {
        Schema::dropIfExists('comments');
    }
}

これでマイグレーションファイルの作成は完了しました。
下記のコマンドによりマイグレーションを実行します。

$ php artisan migrate

Migration table created successfully.
Migrating: 2018_12_02_190928_create_posts_table
Migrated:  2018_12_02_190928_create_posts_table
Migrating: 2018_12_02_190934_create_comments_table
Migrated:  2018_12_02_190934_create_comments_table

上記のように返答が返ってくればテーブルが作成されています。

モデルの作成

テーブルを作成しましたので、それに対応するモデルを作成します。
下記のコマンドを実行してモデルを作成します。

$ php artisan make:model Post
$ php artisan make:model Comment

app/Post.php, app/Comment.phpファイルが作成されました。

app/Post.phpを以下のように設定します。

<?php

namespace App;

use Illuminate\Database\Eloquent\Model;

class Post extends Model
{
    protected $fillable = [
        'title',
        'body',
    ];

    public function comments()
    {
        return $this->hasMany('App\Comment');
    }
}

app/Comment.phpはこちらのように設定します。

<?php

namespace App;

use Illuminate\Database\Eloquent\Model;

class Comment extends Model
{
    protected $fillable = [
        'body',
    ];

    public function post()
    {
        return $this->belongsTo('App\Post');
    }
}

fillableはモデルを利用してデータを作成する時に、複数代入を許可するための設定です。
また、comments, post はテーブル間のリレーションの設定となります。
投稿は複数のコメントを持ち、コメントは一つの投稿に従属します。

Laravelのコマンドについては、こちらの記事でまとめていますので、併せてご覧ください。

【Laravel 5.7】Artisanコンソールの頻出コマンドと使い方

テストデータ作成

開発を進めやすくするため、テストデータを投入しておきます。

下記のコマンドを実行して、ファクトリを作成します。

$ php artisan make:factory PostFactory --model=Post
$ php artisan make:factory CommentFactory --model=Comment

database/migrations/PostFactory.phpdatabase/migrations/CommentFactory.phpが作成されました。それぞれのファイルを下記のように設定します。

# database/migrations/PostFactory.php

<?php

use Faker\Generator as Faker;

$factory->define(App\Post::class, function (Faker $faker) {
    return [
        'title' => '投稿のタイトル',
        'body' => "本文です。テキストテキストテキストテキストテキストテキストテキストテキストテキストテキスト。\nテキストテキストテキストテキストテキストテキストテキストテキストテキストテキスト。テキストテキストテキストテキストテキストテキストテキストテキストテキストテキスト。",
    ];
});


# database/migrations/CommentFactory.php
<?php

use Faker\Generator as Faker;

$factory->define(App\Comment::class, function (Faker $faker) {
    return [
        'body' => "コメントです。テキストテキストテキストテキストテキストテキスト。\nテキストテキストテキストテキストテキストテキストテキストテキストテキストテキストテキストテキスト。",
    ];
});

実行用のシーダークラスを作成します。

$ php artisan make:seeder PostsTableSeeder

database/seeds/PostsTableSeeder.phpファイルが作成されました。下記のように編集します。

<?php

use Illuminate\Database\Seeder;
use App\Post;
use App\Comment;

class PostsTableSeeder extends Seeder
{
    /**
     * Run the database seeds.
     *
     * @return void
     */
    public function run()
    {
        factory(Post::class, 50)
            ->create()
            ->each(function ($post) {
                $comments = factory(App\Comment::class, 2)->make();
                $post->comments()->saveMany($comments);
            });
    }
}

50件の投稿を作成して、各投稿に2つのコメントを作成します。

最後に、database/seeds/DatabaseSeeder.phpを開いて、runメソッドにPostsTableSeederを追加します。

public function run()
{
    $this->call(PostsTableSeeder::class);
}

それでは、下記のコマンドを実行して、テストデータをデータベースに投入しましょう。

$ composer dump-autoload

$ php artisan db:seed

Database seeding completed successfully.と表示されれば完了です。

投稿の一覧

これより画面を作成していきます。Laravelのローカルサーバーを起動しておきます。
こちらのコマンドは開発中は実行したままにしておきます。

$ php artisan serve

まず、投稿の一覧画面を作成しましょう。

最初に、routes/web.phpを開き、ルーティングを設定します。
※ welcomeの記述は使わないので、削除しましょう。

Route::get('/', 'PostsController@index')->name('top');

次にコントローラーを作成します。下記のコマンドを実行しましょう。

$ php artisan make:controller PostsController

app/Http/Controllers/PostsController.phpが作成されました。
下記のように、indexメソッドを追加します。

<?php

namespace App\Http\Controllers;

use Illuminate\Http\Request;
use App\Post;

class PostsController extends Controller
{
    public function index()
    {
        $posts = Post::orderBy('created_at', 'desc')->get();

        return view('posts.index', ['posts' => $posts]);
    }
}

投稿を作成日時の降順で取得して、posts.indexにデータを渡してビューを生成します。

続いてビューを作成します。

その前にレイアウトの共通テンプレートとして、layout.blade.phpを下記のように作成します。bootstrapが利用できるようにCSSを読み込んでいます。

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Laravel BBS</title>

    <link
        rel="stylesheet"
        href="https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0/css/bootstrap.min.css"
        integrity="sha384-Gn5384xqQ1aoWXA+058RXPxPg6fy4IWvTNh0E263XmFcJlSAwiGgFAW/dAiS6JXm"
        crossorigin="anonymous"
    >
</head>
<body>
    <header class="navbar navbar-dark bg-dark">
        <div class="container">
            <a class="navbar-brand" href="{{ url('') }}">
                Laravel BBS
            </a>
        </div>
    </header>

    <div>
        @yield('content')
    </div>
</body>
</html>

では、一覧用のビューとして、resources/views/posts/index.blade.phpファイルを作成して、下記のようにします。

@extends('layout')

@section('content')
    <div class="container mt-4">
        @foreach ($posts as $post)
            <div class="card mb-4">
                <div class="card-header">
                    {{ $post->title }}
                </div>
                <div class="card-body">
                    <p class="card-text">
                        {!! nl2br(e(str_limit($post->body, 200))) !!}
                    </p>
                </div>
                <div class="card-footer">
                    <span class="mr-2">
                        投稿日時 {{ $post->created_at->format('Y.m.d') }}
                    </span>

                    @if ($post->comments->count())
                        <span class="badge badge-primary">
                            コメント {{ $post->comments->count() }}件
                        </span>
                    @endif
                </div>
            </div>
        @endforeach
    </div>
@endsection

http://localhost:8000/アクセスして、下記のように表示されればOKです。

Laravel掲示板 一覧画面

投稿の一覧を取得して、リスト表示しています。
nl2br(e(str_limit($post->body, 200)))は、str_limitメソッドにより投稿の最初の200文字を取得して、改行ありで表示しています。

Bladeテンプレートの使い方は、こちらにまとめていますので併せて参照ください。

Laravel Bladeテンプレートの使い方まとめ

投稿の作成

Laravel掲示板 投稿の作成

次に投稿を作成できるようにします。

投稿の作成画面の表示・作成処理のためのルーティングを追加します。

Route::resource('posts', 'PostsController', ['only' => ['create', 'store']]);

PostsControllerに処理を追加します。
投稿を追加した後は、トップページにリダイレクトするようにします。

public function create()
{
    return view('posts.create');
}

public function store(Request $request)
{
    $params = $request->validate([
        'title' => 'required|max:50',
        'body' => 'required|max:2000',
    ]);

    Post::create($params);

    return redirect()->route('top');
}

続いて、ビューを作成します。

resources/views/posts/create.blade.phpを作成して、以下のように編集します。

@extends('layout')

@section('content')
    <div class="container mt-4">
        <div class="border p-4">
            <h1 class="h5 mb-4">
                投稿の新規作成
            </h1>

            <form method="POST" action="{{ route('posts.store') }}">
                @csrf

                <fieldset class="mb-4">
                    <div class="form-group">
                        <label for="title">
                            タイトル
                        </label>
                        <input
                            id="title"
                            name="title"
                            class="form-control {{ $errors->has('title') ? 'is-invalid' : '' }}"
                            value="{{ old('title') }}"
                            type="text"
                        >
                        @if ($errors->has('title'))
                            <div class="invalid-feedback">
                                {{ $errors->first('title') }}
                            </div>
                        @endif
                    </div>

                    <div class="form-group">
                        <label for="body">
                            本文
                        </label>

                        <textarea
                            id="body"
                            name="body"
                            class="form-control {{ $errors->has('body') ? 'is-invalid' : '' }}"
                            rows="4"
                        >{{ old('body') }}</textarea>
                        @if ($errors->has('body'))
                            <div class="invalid-feedback">
                                {{ $errors->first('body') }}
                            </div>
                        @endif
                    </div>

                    <div class="mt-5">
                        <a class="btn btn-secondary" href="{{ route('top') }}">
                            キャンセル
                        </a>

                        <button type="submit" class="btn btn-primary">
                            投稿する
                        </button>
                    </div>
                </fieldset>
            </form>
        </div>
    </div>
@endsection

一覧画面から、投稿作成画面へのリンクもつけましょう。
resources/views/posts/index.blade.phpを開いて、投稿のリストの上に下記を追加します。

<div class="mb-4">
    <a href="{{ route('posts.create') }}" class="btn btn-primary">
        投稿を新規作成する
    </a>
</div>

これで、投稿を新しく追加できるようになりました。

投稿の詳細・コメントの機能

次に、投稿にコメントを追加する機能を実装します。
コメントは、投稿に複数登録することができ、長くなる場合もありますので、投稿の詳細画面を追加して、そこでコメントを追加できるようにしましょう。

投稿の詳細画面を実装

Laravel掲示板 投稿の詳細

投稿の詳細画面を実装していきます。

投稿の表示のためのルーティングを追加します。
routes/web.phpを開いて、以下のようにshowメソッドにルーティングが通るようにを修正します。

Route::resource('posts', 'PostsController', ['only' => ['create', 'store', 'show']]);

続いて、コントローラーに処理を追加します。
PostsController.phpを開いて、showメソッドを追加します。

public function show($post_id)
{
    $post = Post::findOrFail($post_id);

    return view('posts.show', [
        'post' => $post,
    ]);
}

次に、ビューを追加します。
resources/views/posts/show.blade.phpを作成して、以下のように編集します。

@extends('layout')

@section('content')
    <div class="container mt-4">
        <div class="border p-4">
            <h1 class="h5 mb-4">
                {{ $post->title }}
            </h1>

            <p class="mb-5">
                {!! nl2br(e($post->body)) !!}
            </p>

            <section>
                <h2 class="h5 mb-4">
                    コメント
                </h2>

                @forelse($post->comments as $comment)
                    <div class="border-top p-4">
                        <time class="text-secondary">
                            {{ $comment->created_at->format('Y.m.d H:i') }}
                        </time>
                        <p class="mt-2">
                            {!! nl2br(e($comment->body)) !!}
                        </p>
                    </div>
                @empty
                    <p>コメントはまだありません。</p>
                @endforelse
            </section>
        </div>
    </div>
@endsection

最後に、一覧画面に、投稿の詳細画面へのリンクをつけます。
resources/views/posts/index.blade.phpを開いて、下記のように投稿本文の下にaタグをつけましょう。

<p class="card-text">
    {!! nl2br(e(str_limit($post->body, 200))) !!}
</p>

<a class="card-link" href="{{ route('posts.show', ['post' => $post]) }}">
    続きを読む
</a>

トップページにアクセスして、投稿の一覧と投稿の詳細画面が表示できればOKです。

コメントの追加

Laravel掲示板 コメントフォーム

投稿にコメントを追加する機能を実装します。

ルーティングを追記します。

Route::resource('comments', 'CommentsController', ['only' => ['store']]);

次にコントローラーを作成します。

$ php artisan make:controller CommentsController

CommentsControllerを以下のように編集します。

<?php

namespace App\Http\Controllers;

use Illuminate\Http\Request;
use App\Post;

class CommentsController extends Controller
{
    public function store(Request $request)
    {
        $params = $request->validate([
            'post_id' => 'required|exists:posts,id',
            'body' => 'required|max:2000',
        ]);

        $post = Post::findOrFail($params['post_id']);
        $post->comments()->create($params);

        return redirect()->route('posts.show', ['post' => $post]);
    }
}

投稿の詳細画面に、コメント追加のリクエストを送るためのフォームを追加しましょう。
resources/views/posts/show.blade.phpを開いて、コメントリストの上にフォームを追記します。

<form class="mb-4" method="POST" action="{{ route('comments.store') }}">
    @csrf

    <input
        name="post_id"
        type="hidden"
        value="{{ $post->id }}"
    >

    <div class="form-group">
        <label for="body">
            本文
        </label>

        <textarea
            id="body"
            name="body"
            class="form-control {{ $errors->has('body') ? 'is-invalid' : '' }}"
            rows="4"
        >{{ old('body') }}</textarea>
        @if ($errors->has('body'))
            <div class="invalid-feedback">
                {{ $errors->first('body') }}
            </div>
        @endif
    </div>

    <div class="mt-4">
        <button type="submit" class="btn btn-primary">
            コメントする
        </button>
    </div>
</form>

これで、投稿の詳細画面からコメントを追加できるようになりました。

投稿の編集

Laravel掲示板 編集画面

次に投稿を編集できるようにしてみます。
ルーティングを開いて、edit, updateを追加します。

Route::resource('posts', 'PostsController', ['only' => ['create', 'store', 'show', 'edit', 'update']]);

PostsContolleredit,updateメソッドを追加します。

public function edit($post_id)
{
    $post = Post::findOrFail($post_id);

    return view('posts.edit', [
        'post' => $post,
    ]);
}

public function update($post_id, Request $request)
{
    $params = $request->validate([
        'title' => 'required|max:50',
        'body' => 'required|max:2000',
    ]);

    $post = Post::findOrFail($post_id);
    $post->fill($params)->save();

    return redirect()->route('posts.show', ['post' => $post]);
}

編集画面のビューを作成します。
resources/views/posts/edit.blade.phpを作成して、以下のように編集します。

@extends('layout')

@section('content')
    <div class="container mt-4">
        <div class="border p-4">
            <h1 class="h5 mb-4">
                投稿の編集
            </h1>

            <form method="POST" action="{{ route('posts.update', ['post' => $post]) }}">
                @csrf
                @method('PUT')

                <fieldset class="mb-4">
                    <div class="form-group">
                        <label for="title">
                            タイトル
                        </label>
                        <input
                            id="title"
                            name="title"
                            class="form-control {{ $errors->has('title') ? 'is-invalid' : '' }}"
                            value="{{ old('title') ?: $post->title }}"
                            type="text"
                        >
                        @if ($errors->has('title'))
                            <div class="invalid-feedback">
                                {{ $errors->first('title') }}
                            </div>
                        @endif
                    </div>

                    <div class="form-group">
                        <label for="body">
                            本文
                        </label>

                        <textarea
                            id="body"
                            name="body"
                            class="form-control {{ $errors->has('body') ? 'is-invalid' : '' }}"
                            rows="4"
                        >{{ old('body') ?: $post->body }}</textarea>
                        @if ($errors->has('body'))
                            <div class="invalid-feedback">
                                {{ $errors->first('body') }}
                            </div>
                        @endif
                    </div>

                    <div class="mt-5">
                        <a class="btn btn-secondary" href="{{ route('posts.show', ['post' => $post]) }}">
                            キャンセル
                        </a>

                        <button type="submit" class="btn btn-primary">
                            更新する
                        </button>
                    </div>
                </fieldset>
            </form>
        </div>
    </div>
@endsection

最後に、投稿の詳細画面から編集画面へのリンクを追加します。
resources/views/posts/show.blade.phpを開いて、投稿のタイトルの上あたりに、下記のリンクを追加します。

<div class="mb-4 text-right">
    <a class="btn btn-primary" href="{{ route('posts.edit', ['post' => $post]) }}">
        編集する
    </a>
</div>

以上で、投稿を編集できるようになりました。

投稿の削除

Laravel掲示板 投稿の削除

次に投稿を削除する機能を実装します。

ルーティングにdestroyメソッドを利用できるように追記します。

Route::resource('posts', 'PostsController', ['only' => ['create', 'store', 'show', 'edit', 'update', 'destroy']]);

PostsControllerdestroyメソッドを実装します。

public function destroy($post_id)
{
    $post = Post::findOrFail($post_id);

    \DB::transaction(function () use ($post) {
        $post->comments()->delete();
        $post->delete();
    });

    return redirect()->route('top');
}

投稿の詳細画面に、削除ボタンを設置します。
編集ボタンの右に並ぶ様に、下記のコードをを追記します。

<form
    style="display: inline-block;"
    method="POST"
    action="{{ route('posts.destroy', ['post' => $post]) }}"
>
    @csrf
    @method('DELETE')

    <button class="btn btn-danger">削除する</button>
</form>

以上で、削除機能は完了です。

削除の処理には、投稿と紐づくコメントを削除する必要があり、トランザクションを使いました。トランザクションの使い方については、下記の記事で詳しく説明しています。

Laravelでトランザクション処理の方法をサンプル付きで解説

ページネーションの実装

Laravel掲示板 ページネーション

現状の投稿一覧ですと、投稿が増えていくと処理がどんどん重くなっていきますので、ページネーションをつけてみましょう。

PostsControllerindexメソッド内にて、投稿リストを取得する処理を以下のように変更します。

$posts = Post::orderBy('created_at', 'desc')->paginate(10);

resources/views/posts/index.blade.phpを開いて、投稿リストの下部に追記します。

<div class="d-flex justify-content-center mb-5">
    {{ $posts->links() }}
</div>

これでページネーションが表示されるようになりました。

ページネーションの詳細については、こちらの記事で詳しく説明しています。

Laravelでページネーションを実装する方法

クエリのチューニング

最後に、クエリをチューニングしてみます。

Laravelで実行されているクエリがわかるように、app/Providers/AppServiceProvider.phpを開いて、boot関数を以下のように変更します。

public function boot()
{
    \DB::listen(function ($query) {
        $sql = $query->sql;
        for ($i = 0; $i < count($query->bindings); $i++) {
            $sql = preg_replace("/\?/", $query->bindings[$i], $sql, 1);
        }
        \Log::info($sql);
    });
}

この状態でトップページにアクセスします。
そして、ログファイルをみると以下のように、クエリを12回実行していることがわかります。
※ ログファイルは、storage/logsディレクトリ以下に作成されます。

local.INFO: select count(*) as aggregate from `posts`
local.INFO: select * from `posts` order by `created_at` desc limit 10 offset 0
local.INFO: select * from `comments` where `comments`.`post_id` = 53 and `comments`.`post_id` is not null
local.INFO: select * from `comments` where `comments`.`post_id` = 52 and `comments`.`post_id` is not null
local.INFO: select * from `comments` where `comments`.`post_id` = 51 and `comments`.`post_id` is not null
local.INFO: select * from `comments` where `comments`.`post_id` = 1 and `comments`.`post_id` is not null
local.INFO: select * from `comments` where `comments`.`post_id` = 2 and `comments`.`post_id` is not null
local.INFO: select * from `comments` where `comments`.`post_id` = 3 and `comments`.`post_id` is not null
local.INFO: select * from `comments` where `comments`.`post_id` = 4 and `comments`.`post_id` is not null
local.INFO: select * from `comments` where `comments`.`post_id` = 5 and `comments`.`post_id` is not null
local.INFO: select * from `comments` where `comments`.`post_id` = 6 and `comments`.`post_id` is not null
local.INFO: select * from `comments` where `comments`.`post_id` = 7 and `comments`.`post_id` is not null

なぜこのようなことが起きているかというと、
一覧画面には投稿のリストに加えて、紐づくコメントの合計数を表示しているため、取得した投稿の数だけコメント数をカウントするクエリが発行されてしまっています。

これを解決するために、投稿のリストを取得した時に、紐づくコメントを読み込むようにチューニングしてみます。

PostsControllerindexメソッドで投稿のリストを取得している処理を、以下のように変更します。

$posts = Post::with(['comments'])->orderBy('created_at', 'desc')->paginate(10);

再度トップページにアクセスして、ログファイルを見てみます。

local.INFO: select count(*) as aggregate from `posts`
local.INFO: select * from `posts` order by `created_at` desc limit 10 offset 0
local.INFO: select * from `comments` where `comments`.`post_id` in (1, 2, 3, 4, 5, 6, 7, 51, 52, 53)

クエリの実行回数がが3回だけになったことがわかります。

このような問題をn + 1 問題と言い、Laravelではwithメソッドを利用することで解決することができます。

withメソッドの使い方については、こちらに詳しくまとめています。

Laravel with(Eagerロード)の使い方・サンプル付き

さいごに

長くなりましたが以上で、掲示板を作成するチュートリアルは終了です。

あなたは、記事の通り進め完成させることができましたか?

次の学習ステップとしては、Laravelの本で体系的に機能を把握し、追加機能を実装してみると良いと思います。

人気Laravelの学習におすすめの本を2選!

追加機能の開発では、次のようなことなどをやってみると良いと思います。

  • コメントの編集/削除
  • ユーザー登録

チュートリアルが難しかった方は、スクールでエンジニアのメンタリングを受けながら学習するというのも良い方法です。

注目PHP/Laravelが学べるプログラミングスクールを徹底調査

この記事と関連している記事