[Laravel] FormRequestクラスのまとめ

#今回の題
Laravelのバリデーションで用いるフォームリクエストという機能を解説、まとめた記事です。
ググればたくさん情報が出てきますが、自分の言葉でまとめておきたかったので筆を取りました。
間違いや注意点などありましたらコメントにお願いします🙇‍♀️

#検証したバージョン
Laravel 7.30.0

#フォームリクエストを利用するには

##フォームリクエストの作成
プロジェクトデイレクトリで以下のコマンドを打つと、`app/Http/Request`にStoreBlogPostクラスが作成されます。

```terminal
$ php artisan make:request StoreBlogPost
```

## メソッドにDIする
コントローラーにリクエストを受け取りその内容を保存する`store`というメソッドがあったとします。

```php
    public function store(Request $request)
    {
        // 保存処理
    }
```

そのメソッドのRequestクラスをDIしている箇所を、先ほど作成した`StoreBlogPost`クラスに置き換えれば、保存処理の前にフォームリクエストに定義したバリデーションが適応されるようになります。

```php
    public function store(StoreBlogPost $request)
    {
        // 保存処理
    }

```


#使い方
フォームリクエストは初期状態だと以下のようになっています。

```php
<?php

namespace App\Http\Requests;

use Illuminate\Foundation\Http\FormRequest;

class StoreBlogPost extends FormRequest
{
    /**
     * Determine if the user is authorized to make this request.
     *
     * @return bool
     */
    public function authorize()
    {
        return false;
    }

    /**
     * Get the validation rules that apply to the request.
     *
     * @return array
     */
    public function rules()
    {
        return [
            //
        ];
    }
}
```

定義されているメソッドは2つ、

## authorize()

リクエストを行ったユーザーの権限を確かめるメソッドです。
falseを返すとアクセスが拒否されたことを示す403エラーを吐き、
trueを返すと認可してバリデーションを行います。
認証をコントローラーやポリシーなどで行っている場合は恒常でtrueを返しておきます。

```php
    public function authorize()
    {
        return true;
    }
```


## rules()

バリデーションのルールを記載するメソッドです。
前提として以下のようなformがあったとします。

```php
<form action="" method="POST">
    <input type="text" name="title">
    <textarea name="body"></textarea>
</form>
```

この内容に対して適当なバリデーションをあててみます。

```php

    public function rules()
    {
        return [
            'title' => 'required | unique:posts | max:255',
            'body' => 'required',
        ];
    }
```

上記のように`'項目名' => 'ルール'`の形で記入し、ルールが複数あるときは`|`を使い`'ルール|ルール'`といった具合に書きます。

このコードで各項目にあてられたバリデーションは以下のようになっています。

- title
`入力必須` 
`postsテーブルにてユニークな(重複しない)値`
`255字以内`


- body
`入力必須` 

使用できるルールは[ここ](https://readouble.com/laravel/7.x/ja/validation.html)で確認できます。

#オーバーライドして使用できるメソッド
## attributes()

バリデーションメッセージ内に表示される項目名はそのままだと`title`や`body`のままですが、このメソッドから任意の名前にカスタマイズすることが可能です。

```php
    public function attributes()
    {
        return [
            'title' =>'タイトル',
        ];
    }
```

## messages()

バリデーションで弾かれた場合、ユーザーはバリデーションメッセージを抱えた状態で直前のページにリダイレクトされます。
その時のメッセージをカスタマイズするメソッドです。

```php
    public function messages()
    {
        return [
            'title.required' => 'タイトルは必須です',
            'title.unique' =>'既に存在するタイトルです',
        ];
    }
```

上記のように`項目名.ルール`の形で記入します。

## prepareForValidation()

バリデーション前にデータを加工する際に用いるメソッドです。

```php
    protected function prepareForValidation()
    {
        $this['user_id'] = Auth::id();
    }
```
例としてリクエストにログインユーザーのidを追加してみました。

# 配列に対してバリデーションを行う
おまけです。
前提として以下のような画像複数枚を配列で送信するformがあるとします。

```php
<form action="" method="POST" enctype="multipart/form-data">
    <input type="file" name="images[]">
    <input type="file" name="images[]">
    <input type="file" name="images[]">
</form>
```

この配列の一つ一つにバリデーションを行うには以下のようにします。

```php
    public function rules()
    {
        return [
            'images.*' => 'image | mimes:jpeg,png,jpg'
        ];
    }
```
全部に同じルールを適応するのであれば`'項目.*'`とし、一つ一つに行うのであれば`項目.配列の添字番号`とします。


#参考
[Illuminate/Foundation/Http/FormRequest.php](https://github.com/laravel/framework/blob/7.x/src/Illuminate/Foundation/Http/FormRequest.php)
[readouble](https://readouble.com/laravel/7.x/ja/validation.html)

#一言
何か面白いメソッドないかとソース見ましたが、特になかったためほぼreadoubleに乗っている内容になりました🚗