Help us understand the problem. What is going on with this article?

Laravelにおける複数フィールドの最低限必須のバリデーション

TL;DR

required_without_allルールを使いましょう。

required_without_allルールについてと挙動の確認

スクリーンショット 2019-11-27 11.43.08.png

公式ドキュメントを丹念に探せば見つかるのですが、わかりづらいバリデーションとして、
複数あるフィールドの中で、最低限ひとつは入力してもらいたい場合をチェックするバリデーションがあると思います。
例えば上のキャプチャのような、いくつかのSNSアカウントを入力するフィールドがあって、その中のどれかひとつでも入力してくれればオーケーみたいな場合です。
これはrequired_without_allルールでバリデーションできます。

https://laravel.com/docs/6.x/validation#rule-required-without-all
https://readouble.com/laravel/6.x/ja/validation.html#rule-required-without-all

指定した他のフィールドがすべて存在していない場合、このフィールドが存在し、かつ空でないことをバリデートします。

よく読めばこれが求めていたルールです! と納得するのですが、流し見程度だとちょっとわかりづらい。。
そこで今回はフォームリクエストのサンプルを作り、それをテストしてrequired_without_allルールの動きを確認します。
尚、Laravelのバージョンは6です。

$ php artisan make:request SampleFormRequest
Request created successfully.
$ php artisan make:test --unit SampleFormRequestTest
Test created successfully.
<?php

namespace App\Http\Requests;

use Illuminate\Foundation\Http\FormRequest;

class SampleFormRequest 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
     */
    public function rules()
    {
        return [
            'qiita'     => 'required_without_all:github,twitter,instagram',
            'github'    => '',
            'twitter'   => '',
            'instagram' => '',
        ];
    }

    public function messages()
    {
        return [
            'qiita.required_without_all' => 'Qiita / GitHub / Twitter / Instagramの中で1個以上の項目を必ず入力してください。',
        ];
    }
}

required_without_allのパラメータで他の項目を羅列します。

<?php

namespace Tests\Unit;

use Tests\TestCase;
use Illuminate\Support\Facades\Validator;
use App\Http\Requests\SampleFormRequest;

class SampleFormRequestTest extends TestCase
{
    /**
     * required_without_allルールのフォームリクエストのテスト
     *
     * @dataProvider validationDataProvider
     *
     * @param array $inputs
     * @param array $expected
     * @return void
     */
    public function testValidation(array $inputs, array $expected)
    {
        $request   = new SampleFormRequest();
        $validator = Validator::make($inputs, $request->rules(), $request->messages());
        $result    = $validator->passes();
        $errors    = $validator->errors();

        $this->assertEquals($expected['response'], $result);
        $this->assertEquals($expected['errors'], $errors->toArray());
    }

    public function validationDataProvider()
    {
        return [
            'エラー' => [
                [
                    'qiita'     => '',
                    'github'    => '',
                    'twitter'   => '',
                    'instagram' => '',
                ],
                [
                    'response' => false,
                    'errors'   => [
                        'qiita' => ['Qiita / GitHub / Twitter / Instagramの中で1個以上の項目を必ず入力してください。'],
                    ]
                ]
            ],
            '正常1' => [
                [
                    'qiita'     => 'kiyc',
                    'github'    => '',
                    'twitter'   => '',
                    'instagram' => '',
                ],
                [
                    'response' => true,
                    'errors'   => []
                ]
            ],
            '正常2' => [
                [
                    'qiita'     => '',
                    'github'    => 'kiyc',
                    'twitter'   => '',
                    'instagram' => '',
                ],
                [
                    'response' => true,
                    'errors'   => []
                ]
            ],
        ];
    }
}
$ vendor/bin/phpunit tests/Unit/SampleFormRequestTest.php 
PHPUnit 8.4.1 by Sebastian Bergmann and contributors.

...                                                                 3 / 3 (100%)

Time: 396 ms, Memory: 16.00 MB

OK (3 tests, 6 assertions)

すべて未入力だとエラーになり、ルールを指定したフィールドに入力がある場合、またはルールを指定していないフィールドに入力がない場合でもエラーにならないことを確認できました:beer:
このルールを見つけられなかったばかりに、私はわざわざカスタムルールを作ってしまったので、皆さん公式ドキュメントはしっかり読みましょう:scroll:

Why not register and get more from Qiita?
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away
Comments
No comments
Sign up for free and join this conversation.
If you already have a Qiita account
Why do not you register as a user and use Qiita more conveniently?
You need to log in to use this function. Qiita can be used more conveniently after logging in.
You seem to be reading articles frequently this month. Qiita can be used more conveniently after logging in.
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away
ユーザーは見つかりませんでした