Developer

Laravelで簡単な掲示板を作成の巻 第3話 魁!小野の塾
2022.10.07
Lv2

Laravelで簡単な掲示板を作成の巻 第3話 魁!小野の塾

Laravelで簡単な掲示板を作成

魁!小野の塾 PHPで簡単なプログラムを作ってみようの巻 第1話 では、簡単な掲示板をPHPで作成しました。

今回は、同じような機能をLaravelで構築していきます。
機能的には、登録処理、削除処理、エラーチェックなどを実装していきます。

前回のソースは、200行程度の1ファイルだったのですが、今回はどのように書き方が変わるのか、見ていければ良いかと思います。
また、フレームワークを利用する機会は増えましたので、しっかり開発手順を覚えて頂きたいです。

Bootstrapを利用したサンプルを作成していますが、Laravelは Tailwind をCSSのフレームワークとして押しています。
Tailwindはコンポーネント開発を前提としたCSSフレームワークで、CSSを知っている人には使いやすいですが、Bootstrapを長年利用している人には、少し難易度が高いと思います。

対象のスキルレベル

構築環境

  • Windows10
  • XAMPP 8.1.2(PHP 8.1.2, MariaDB 10.4.22)
  • Laravel v9.33.0

登録処理作成

登録処理から実装していきます。
登録処理には、Blade(View)の作成、Validation、DBへの登録処理があり、順番に実装していきます。

resources/views/bbs.blade.php Bladeの実装

登録処理、エラー表示部分の実装を行います。

24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
・・省略・・
<body>
    <header>
        <nav class="navbar navbar-expand-lg navbar-dark bg-success fixed-top">
            <section class="container">
                <a class="navbar-brand" href="#">
                    <h1 class="animate__animated animate__backInRight"><i class="far fa-clipboard"></i> 掲示板</h1>
                </a>
                <button class="navbar-toggler" type="button" data-toggle="collapse" data-target="#navbarText" aria-controls="navbarText" aria-expanded="false" aria-label="Toggle navigation">
                    <span class="navbar-toggler-icon"></span>
                </button>
                <div class="collapse navbar-collapse" id="navbarText">
                    <span class="navbar-text animate__animated animate__bounce animate__delay-3s">
                        <i class="fas fa-heart"></i> 好きなこと書いて生きよう!
                    </span>
                </div>
            </section>
        </nav>
    </header>
    <main class="container">
        @if ($errors->any())
        <div class="alert alert-danger" role="alert">
            <h4 class="alert-heading"><i class="fas fa-exclamation-triangle"></i> エラー</h4>
            <ul>
                @foreach($errors->all() as $error)
                <li>{{ $error }}</li>
                @endforeach
            </ul>
        </div>
        @endif
・・省略・・

エラー表示部分(44-53)

Bladeでは、@~という構文が用意されています。ifとかforeachなど色々あります。
普通にif文を書く感覚で利用できるのですが、@if ~ @endif と終了のコードを書く必要があります。
通常のPHPの場合は、{ } ブロックにて開始、終了を決定するのに対して、少し厄介かもしれません。
慣れるまではしっかりと、終了コードを書くことを意識するようにして下さい。(忘れがちです)

Laravelでは、Validationのエラー内容は、$errors 変数に入ります。
any() 関数では、エラーがある場合に、true ない場合に false が返ります。

44行目のif文は、エラーがある場合という意味になります。

エラーの内容を全て取り出すには、all() 関数を利用します。
@foreach 構文は、通常の foreach と同様に書くことができます。
ただ、if文と同様に終了コードを書く必要があることを意識してください。

{{ $error }} では、エラーの内容を echo しています。
<?= htmlspecialchars($error) ?> と同様な意味になります。

Blade参考 (Laravel公式)

Laravel Blade
@ Bladeディレクティブ

54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
・・省略・・
        <form method="post">
            @csrf
            <div class="form-group row mb-3">
                <label for="title" class="col-sm-2 col-form-label">タイトル</label>
                <div class="col-sm-10">
                    <input type="text" name="title" class="form-control" id="title" placeholder="タイトル" value="{{ old('title') }}" autofocus>
                </div>
            </div>
            <div class="form-group row mb-3">
                <label for="contents" class="col-sm-2 col-form-label">内容</label>
                <div class="col-sm-10">
                    <textarea name="contents" class="form-control" id="contents" rows="10" placeholder="内容を入力してください">{{ old('contents') }}</textarea>
                </div>
            </div>
            <div class="form-group row">
                <div class="offset-sm-2 col-sm-10">
                    <button type="submit" class="btn btn-primary"><i class="fas fa-paper-plane"></i> 送信</button>
                </div>
            </div>
        </form>
 
        <div class="mt-5"></div>
    </main>
・・省略・・

入力フォーム部分

登録処理は、Controller#storeを呼び出すのですが、URLは /bbs で HTTP METHOD は POST になります。
action属性は指定していないと、現在のURLに対して送信を行いますので、action属性が未指定になっています。

@csrf は、クロスサイト・リクエスト・フォージェリー対応です。
この記述を忘れると、Laravel側でエラーを出力します。

name属性には、テーブルの項目名を設定します。これで、モデルと紐づいて、データベースに登録が可能です。

{{ old(key) }} old関数は、form送信時にエラーがある場合に、その入力値を表示してくれます。
第2引数にデフォルト値を設定することもできます。
例えば、初期表示時に「へのへのもへじ」と表示したい場合、{{ old(‘title’, ‘へのへのもへじ’) }} とすると、初期表示では「へのへのもへじ」と表示され、入力値がエラーの場合のみ、入力値が表示されます。

app/Http/Requests/StoreBbsRequest.php Validationの実装

エラーチェック部分を実装します。
Controllerを作成するときのコマンドで、–requests オプションを指定すると、リクエストのエラーチェックを自動で行ってくれるクラスを自動生成できます。

  • 登録用 StoreBbsRequest.php
  • 更新用 UpdateBbsRequest.php

今回は、更新処理がないので、登録用の StoreBbsRequest.php のみを変更していきます。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
<?php
 
namespace App\Http\Requests;
 
use Illuminate\Foundation\Http\FormRequest;
 
class StoreBbsRequest extends FormRequest
{
    /**
     * Determine if the user is authorized to make this request.
     *
     * @return bool
     */
    public function authorize()
    {
        return true;
    }
 
    /**
     * Get the validation rules that apply to the request.
     *
     * @return array<string, mixed>
     */
    public function rules()
    {
        return [
            'title'     => 'required|max:255',
            'contents'  => 'required|max:65535',
        ];
    }
 
    public function messages()
    {
        return [
            'title.required'    => 'タイトルを入力して下さい。',
            'title.max'         => 'タイトルは:max文字以内で入力してください。',
            'contents.required' => '本文を入力して下さい。',
            'contents.max'      => '本文は:max文字以内で入力して下さい。',
        ];
    }
}

authorize(16)

デフォルトは、return false; となっています。今回はログイン機能を実装しない為、true を返すように変更します。
なお、変更しない場合は、認証エラーとなります。変更後は、未ログイン状態でも実行できるようになります。

rules(27-28)

項目名に対して、チェック内容を記載します。複数ある場合は、パイプ記号 ( | ) で区切ります。
今回は、必須チェック (required) と最大文字数チェック (max) を入れていきます。

messages(32-40)

日本語化を行う方法は、別にあるのですが、今回は項目数もチェック内容も少ないので、この関数を作成し、エラーメッセージを日本語化しています。
項目名.チェックタイプ の指定で、エラーメッセージを書いていきます。

app/Http/Controllers/BbsController.php Controllerの実装

最後に登録処理の実態を作成します。
登録処理は、Controllerの store 関数に作成しています。

30
31
32
33
34
35
36
37
38
39
40
41
42
43
・・省略・・
    /**
     * Store a newly created resource in storage.
     *
     * @param  \App\Http\Requests\StoreBbsRequest  $request
     * @return \Illuminate\Http\Response
     */
    public function store(StoreBbsRequest $request)
    {
        $bbs = new Bbs();               // Modelをインスタンス化
        $bbs->create($request->all());  // requestからfillを通してモデルを作成後、登録処理
        return redirect('/bbs');        // indexへリダイレクトします
    }
・・省略・・

モデルをインスタンス後に、create 関数を利用してデータベースへ登録します。
リクエスト情報から、モデルの項目名に紐づくデータを取得して、モデルを作成してくれます。この際に、モデルに定義した $fillable の内容を利用します。
$fillable が未設定の場合は、リスエスト自体に @csrf が含まれており、_token という名前で、パラメータが送信されます。
モデルに存在しないキー名なので、$reqest->all() を利用する場合は、エラーになります。

$fillable を定義したくない場合は、$request から指定キーの配列を作成すれば良いのですが、モデルに定義しておいた方が簡単かと思います。
Laravelでは固定の書き方はなく、柔軟なコーディングが可能になっていますので、他のサンプルなどもみて、自分の好きなコードの書き方を研究してください。

最後に、/bbs のURLに対してリダイレクトして終了です。

次回は、リスト表示の実装と、削除機能の実装を行います。

魁!小野の塾 連載目次リンク