Попытка переноса проверки с контроллера на класс запроса в Laravel 5.2.15

У меня очень простой метод Rule в классе запросов, как показано ниже.

public function rules()
{
    return [
        'Subject'           => 'required|max:50',
        'Description'       => 'required|max:500',
        'DepartmentID'      => 'required|integer|min:1',
        'PriorityID'        => 'required|integer|min:1'
    ];
}

Метод управления внутри контроллера. Ниже приведен код.

private function SaveChanges(\App\Http\Requests\TicketRequest $request) {

    $v = \Validator::make($request->all(), [
    ]);

    $DepartmentAdmins = $this->getDepartmentAdmins();

    //Check if department admin missing then no need to add the record
    if($DepartmentAdmins == null || count($DepartmentAdmins) == 0) {
        $v->errors()->add('MissingAdmins', 'Department admin missing.');
        return redirect()->back()->withErrors($v->errors());
    }
}

Вопрос:

Как мы видим в методе rule, существует 4 поля формы. Есть ли способ сдвинуть проверку существования администратора Admin с помощью метода Action Control на класс request?

Ответ 1

Laravel Request имеет крючок after, который можно запустить после завершения обычной проверки. Вот как вы можете использовать его в своем случае:

namespace App\Http\Requests;

use App\Http\Requests\Request;
use App\Models\Property;
use Illuminate\Validation\Validator;

class SomeRequest extends Request
{
    /**
     * Get the validator instance for the request.
     *
     * @return Validator
     */
    protected function getValidatorInstance()
    {
        $instance = parent::getValidatorInstance();
        $instance->after(function ($validator) {
            $this->validateDepartmentAdmins($validator);
        });

        return $instance;
    }

    public function authorize()
    {
        return true;
    }

    /**
     * Get the validation rules that apply to the request.
     *
     * @return array
     */
    public function rules()
    {
        return [
            'Subject'           => 'required|max:50',
            'Description'       => 'required|max:500',
            'DepartmentID'      => 'required|integer|min:1',
            'PriorityID'        => 'required|integer|min:1'
        ];
    }

    /**
     * @param Validator $validator
     */
    public function validateDepartmentAdmins(Validator $validator)
    {
        $DepartmentAdmins = $this->getDepartmentAdmins();

        //Check if department admin missing then no need to add the record
        if($DepartmentAdmins == null || count($DepartmentAdmins) == 0) {
            $validator->errors()->add('MissingAdmins', 'Department admin missing.');
        }
}

Таким образом, вам не придется выполнять какую-либо проверку в вашем контроллере SaveChanges.

Этот код используется в Laravel 5.1, но я считаю, что он будет работать в 5.2.

Ответ 2

Класс запроса формы в основном имеет два метода. "разрешать" и "правила". лучший способ перенести проверку на Office Admin existense - добавить свой собственный валидатор (например, с именем "adminCountValidator" ) и реализовать свою логику для проверки количества администраторов. Затем используйте новый валидатор yoir в методе "rules" следующим образом:

public function rules()
{
    return [
        'Subject'           => 'required|max:50',
        'Description'       => 'required|max:500',
        'DepartmentID'      => 'required|integer|min:1|adminCountValidator',
        'PriorityID'        => 'required|integer|min:1'
    ];
}

если вы определяете правило проверки custome, вы также можете определить связанное сообщение об ошибке, и действие вашего контроллера будет намного более чистым. вот ссылка для определения собственного пользовательского валидатора
custom-validation-rules

здесь приведен пример кода для добавления пользовательского валидатора в поставщика услуг

    class AppServiceProvider extends ServiceProvider
{
    public function boot()
    {
        Validator::extend('adminCountValidator', function($attribute, $value, $parameters, $validator) {
            /*
           implement your getDepartmentAdmins() 
           function here and return true or false
            */
            });
    }