Подтвердить что ты не робот

Как добавить пользовательские правила валидации при использовании проверки формы запроса в Laravel 5

Я использую метод проверки формы запроса для проверки запроса в laravel 5. Я хотел бы добавить свое собственное правило проверки с помощью метода проверки формы. Ниже приведен мой класс запроса. Я хочу добавить пользовательскую проверку numeric_array с элементами поля.

  protected $rules = [
      'shipping_country' => ['max:60'],
      'items' => ['array|numericarray']
];

Моя функция cusotom приведена ниже

 Validator::extend('numericarray', function($attribute, $value, $parameters) {
            foreach ($value as $v) {
                if (!is_int($v)) {
                    return false;
                }
            }
            return true;
        });

Как использовать этот метод проверки с помощью проверки формы запроса в laravel5?

4b9b3361

Ответ 1

Использование Validator::extend(), как и вы, на самом деле прекрасно, вам просто нужно поместить это в Поставщик услуг следующим образом:

<?php namespace App\Providers;

use Illuminate\Support\ServiceProvider;

class ValidatorServiceProvider extends ServiceProvider {

    public function boot()
    {
        $this->app['validator']->extend('numericarray', function ($attribute, $value, $parameters)
        {
            foreach ($value as $v) {
                if (!is_int($v)) {
                    return false;
                }
            }
            return true;
        });
    }

    public function register()
    {
        //
    }
}

Затем зарегистрируйте поставщика, добавив его в список в config/app.php:

'providers' => [
    // Other Service Providers

    'App\Providers\ValidatorServiceProvider',
],

Теперь вы можете использовать правило проверки numericarray везде, где хотите

Ответ 2

В то время как приведенный выше ответ верен, во многих случаях вам может потребоваться создать пользовательскую проверку только для определенного запроса формы. Вы можете использовать laravel FormRequest и использовать инъекцию зависимостей для расширения проверки factory. Я думаю, что это решение намного проще, чем создание поставщика услуг.

Вот как это можно сделать.

use Illuminate\Validation\Factory as ValidationFactory;

class UpdateMyUserRequest extends FormRequest {

    public function __construct(ValidationFactory $validationFactory)
    {

        $validationFactory->extend(
            'foo',
            function ($attribute, $value, $parameters) {
                return 'foo' === $value;
            },
            'Sorry, it failed foo validation!'
        );

    }

    public function rules()
    {
        return [
            'username' => 'foo',
        ];
    }
}

Ответ 3

Принятый ответ работает для глобальных правил проверки, но много раз вы будете проверять определенные условия, которые очень специфичны для формы. Вот то, что я рекомендую в этих обстоятельствах (что, похоже, несколько связано с исходным кодом Laravel на строка 75 формы FormRequest.php):

Добавить метод проверки подлинности родительскому запросу. Запросы ваших запросов будут расширяться:

<?php namespace App\Http\Requests;

use Illuminate\Foundation\Http\FormRequest;
use Validator;

abstract class Request extends FormRequest {

    public function validator(){

        $v = Validator::make($this->input(), $this->rules(), $this->messages(), $this->attributes());

        if(method_exists($this, 'moreValidation')){
            $this->moreValidation($v);
        }

        return $v;
    }
}

Теперь все ваши конкретные запросы будут выглядеть так:

<?php namespace App\Http\Requests;

use App\Http\Requests\Request;

class ShipRequest extends Request {

    public function rules()
    {
        return [
            'shipping_country' => 'max:60',
            'items' => 'array'
        ];
    }

    // Here we can do more with the validation instance...
    public function moreValidation($validator){

        // Use an "after validation hook" (see laravel docs)
        $validator->after(function($validator)
        {
            // Check to see if valid numeric array
            foreach ($this->input('items') as $item) {
                if (!is_int($item)) {
                    $validator->errors()->add('items', 'Items should all be numeric');
                    break;
                }
            }
        });
    }

    // Bonus: I also like to take care of any custom messages here
    public function messages(){
        return [
            'shipping_country.max' => 'Whoa! Easy there on shipping char. count!'
        ];
    }
}

Ответ 4

Вам необходимо переопределить метод getValidatorInstance в вашем классе Request, например, следующим образом:

protected function getValidatorInstance()
{
    $validator = parent::getValidatorInstance();
    $validator->addImplicitExtension('numericarray', function($attribute, $value, $parameters) {
        foreach ($value as $v) {
            if (!is_int($v)) {
                return false;
            }
        }
        return true;
    });

    return $validator;
}

Ответ 5

Вам не нужно расширять валидатор для проверки элементов массива, вы можете проверить каждый элемент массива на "*", как вы можете видеть в Проверка массива

protected $rules = [
      'shipping_country' => ['max:60'],
      'items' => ['array'],
      'items.*' => 'integer'
];

Ответ 6

Для меня работает решение, которое дает нам lukasgeiter, но с той разницей, что мы создаем класс с нашими пользовательскими проверками, например, для laravel 5.2. * Следующий пример - добавить проверку на диапазон дат, в котором вторая дата должна быть равной или более большой, чем первая.

В приложении/Провайдерах создайте ValidatorExtended.php

<?php
namespace App\Providers;
use Illuminate\Validation\Validator as IlluminateValidator;

class ValidatorExtended extends IlluminateValidator {

private $_custom_messages = array(
 "after_or_equal" => ":attribute debe ser una fecha posterior o igual a 
 :date.",
);

public function __construct( $translator, $data, $rules, $messages = array(),      
$customAttributes = array() ) {
  parent::__construct( $translator, $data, $rules, $messages, 
  $customAttributes );
  $this->_set_custom_stuff();
}

protected function _set_custom_stuff() {
   //setup our custom error messages
  $this->setCustomMessages( $this->_custom_messages );
}

/**
 * La fecha final debe ser mayor o igual a la fecha inicial
 *
 * after_or_equal
 */
protected function validateAfterOrEqual( $attribute, $value, $parameters, 
$validator) {
   return strtotime($validator->getData()[$parameters[0]]) <= 
  strtotime($value);
}

}   //end of class

Ok. теперь создайте поставщика услуг. Создайте ValidationExtensionServiceProvider.php внутри приложения/Провайдеров, и мы закодируем

<?php
namespace App\Providers;

use Illuminate\Support\ServiceProvider;
use Validator;

class ValidationExtensionServiceProvider extends ServiceProvider {

public function register() {}

public function boot() {
  $this->app->validator->resolver( function( $translator, $data, $rules, 
  $messages = array(), $customAttributes = array() ) {
    return new ValidatorExtended( $translator, $data, $rules, $messages, 
    $customAttributes );
} );
}

}   //end of class

Теперь мы расскажем Laravel о загрузке этого поставщика услуг, добавим массив провайдеров в конец в config/app.php и

//Servicio para extender validaciones
App\Providers\ValidationExtensionServiceProvider::class,

теперь мы можем использовать эту проверку в нашем запросе в правилах функций

public function rules()
{
  return [
    'fDesde'     => 'date',
    'fHasta'     => 'date|after_or_equal:fDesde'
 ];
}

или в Validator: make

$validator = Validator::make($request->all(), [
    'fDesde'     => 'date',
    'fHasta'     => 'date|after_or_equal:fDesde'
], $messages);

вы должны заметить, что имя метода, которое делает проверку, имеет префикс validate и находится в стиле верблюда case validateAfterOrEqual, но когда вы используете правило проверки, каждая заглавная буква заменяется символом подчеркивания и буквой в строчной букве.

Все это я беру от https://www.sitepoint.com/data-validation-laravel-right-way-custom-validators// здесь, объясняя подробности. благодаря им.