Be part of JetBrains PHPverse 2026 on June 9 – a free online event bringing PHP devs worldwide together.

imJohnBon's avatar

Resolving Multiple Custom Validators?

So I have the need to create some custom validators in my Laravel build, so I've created them and then resolved them in a ValidationServiceProvider:


namespace App\Providers;

use Illuminate\Support\ServiceProvider;
use App\Validators\VideoValidator;
use App\Validators\ZipcodeValidator;

class ValidationServiceProvider extends ServiceProvider {

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

        $this->app->validator->resolver(function($translator, $data, $rules, $messages)
        {
            return new ZipcodeValidator($translator, $data, $rules, $messages);
        });
    }

    public function register()
    {
    }

}

The problem is, the site now throws an error when I attempt to use both of them together. They each work without the other, but if I try to validate fields in a form using both of them I get an Exception.

My best guess is that I'm using the resolver method twice, and maybe it's only supposed to be used once? But it can only have 1 return, so how am I supposed to do that?

0 likes
12 replies
usman's avatar

You can use the two custom factories by extending the Illuminate\Validation\Factory and override the resolve method to return an instance of your custom validator. For instance,

<?php namespace App\Validators\Factories;

use App\Validators\VideoValidator;
use Illuminate\Validation\Factory;

class VideoValidatorFactory extends Factory {

    protected function resolve(array $data, array $rules, array $messages, array $customAttributes)
    {
            return new VideoValidator($this->translator, $data, $rules, $messages, $customAttributes);

    }
}

Also, you will need to register the binding with the IoC, which you can do inside the AppServiceProvider, or maybe use a custom one. Just an opinion, Regards!

imJohnBon's avatar

@bestmomo Yeah I had seen that, but damn, it really is a pretty ugly solution. It seems weird for the framework to basically only allow 1 custom validator or else you need to sort of hack around it. There must be plenty of cases out there were multiple custom validators are needed.

imJohnBon's avatar

@bestmomo Also doesn't this solution break completely when you need to use 2 different custom validators on the same form?

thepsion5's avatar
Level 25

I've solved this before by using a single custom validator with multiple validation methods and using extend() rather than resolve(). My service provider:

public function boot()
{
     /* snip */
    $this->registerValidationRules($this->app['validator']);
}

protected function registerValidationRules(\Illuminate\Contracts\Validation\Factory $validator)
{
    $validator->extend('zip', 'Gvt\Support\Validators\GvtRuleValidator@validateZip');
    $validator->extend('state', 'Gvt\Support\Validators\GvtRuleValidator@validateStateCode');
    $validator->extend('phone', 'Gvt\Support\Validators\GvtRuleValidator@validatePhone');
    $validator->extend('county', 'Gvt\Support\Validators\GvtRuleValidator@validateCounty');
    $validator->extend('party', 'Gvt\Support\Validators\GvtRuleValidator@validatePoliticalParty');
    $validator->extend('ballot_style', 'Gvt\Support\Validators\GvtRuleValidator@validateBallotStyle');
}
6 likes
imJohnBon's avatar

@thepsion5 Thanks! This appears to be much cleaner. 3 things:

1) Looks like there's a typo in the code. Validation is misspelled in the function you declared.

2) You inject a $factory variable into the function, but then use one called $validator. I'm assuming these should be the same.

3) I believe you should use the contract (Illuminate\Contracts\Validation\Factory) and not the direction implementation of that class.

Primarily though, when I try to implement this, I get the following error:

BindingResolutionException in Container.php line 872:
Unresolvable dependency resolving [Parameter #1 [  array $data ]] in class Illuminate\Validation\Validator

Has this actually worked for you in the past with Laravel 5?

imJohnBon's avatar

@thepsion5 Hmm I'm beginning to wonder if my error even has anything to do with your method. Because even when I do this in my routes file:

Validator::extend('video', 'App\Validators\VideoValidator@validate');

I get the same error as my above message. Now I'm wondering if this is some remaining bug with L5 or not.

imJohnBon's avatar

Annnd I figured it out, god freakin' damnit. A word for everyone else, if you EXTEND the validator and use a class to do so (instead of a closure), said class should NOT extend the validator class (which is the opposite of when you resolve it with a class as I was originally doing, it then does need to extend the validator class). For instance, my original ZipcodeValidator class looked like this:

namespace App\Validators;

use Illuminate\Validation\Validator;

class VideoValidator extends Validator {

    public function validate($attribute, $value)
    {
    }

}

When actually it should have looked like this:

namespace App\Validators;

class VideoValidator {

    public function validate($attribute, $value)
    {
    }

}

It should just be a plain old class.

@thepsion5 If you could quickly fix the errors in your code I outlined earlier, I will happily mark your answer as the winner.

1 like
Gaines12's avatar

Hmmm, what if I still want to extend the class though? I'm wanting to add my own custom error messages and submit my new validate method as an implicit rule. Would I need to extend (with a resolver this time) the class with another class??

EDIT: It appears that Validator has an extendImplicit method which solves this problem.

Please or to participate in this conversation.