You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Laravel 9:如何在自定义验证规则中调用已有验证规则?

在Laravel 9中实现UsernameOrEmail自定义验证规则

下面提供两种合规的实现方案,替代你原本调用受保护方法validateAttribute的思路:

方案一:直接调用规则自身的验证逻辑

自定义规则类(如Username)和Laravel内置的Email规则都具备独立的验证能力,无需依赖外部Validator实例,实现更轻量化:

基于Rule接口的实现

use Illuminate\Contracts\Validation\Rule;
use Illuminate\Validation\Rules\Email;

class UsernameOrEmail implements Rule
{
    /**
     * 验证字段是否有效
     *
     * @param  string  $attribute
     * @param  mixed  $value
     * @return bool
     */
    public function passes($attribute, $value)
    {
        // 验证邮箱格式
        $emailValidation = (new Email())->passes($attribute, $value);
        // 验证用户名格式
        $usernameValidation = (new Username())->passes($attribute, $value);

        return $emailValidation || $usernameValidation;
    }

    /**
     * 返回错误提示信息
     *
     * @return string
     */
    public function message()
    {
        return 'The :attribute is not a valid username or email.';
    }
}

可调用规则的实现(Laravel 9推荐方式)

use Illuminate\Validation\Rules\Email;

class UsernameOrEmail
{
    /**
     * 执行验证
     *
     * @param  string  $attribute
     * @param  mixed  $value
     * @param  \Closure  $fail
     * @return void
     */
    public function __invoke($attribute, $value, $fail)
    {
        $isValidEmail = (new Email())->passes($attribute, $value);
        $isValidUsername = (new Username())->passes($attribute, $value);

        if (!$isValidEmail && !$isValidUsername) {
            $fail('The :attribute is not a valid username or email.');
        }
    }
}

方案二:利用临时Validator实例验证

如果需要复用现有Validator的配置上下文,可以创建临时Validator实例来测试字段值:

use Illuminate\Support\Facades\Validator;

class UsernameOrEmail
{
    protected $validator;

    public function setValidator($validator)
    {
        $this->validator = $validator;
        return $this;
    }

    public function __invoke($attribute, $value, $fail)
    {
        // 验证邮箱
        $emailCheck = Validator::make(
            [$attribute => $value],
            [$attribute => 'email']
        )->passes();

        // 验证用户名
        $usernameCheck = Validator::make(
            [$attribute => $value],
            [$attribute => new Username()]
        )->passes();

        if (!$emailCheck && !$usernameCheck) {
            $fail('The :attribute is not a valid username or email.');
        }
    }
}

关键说明

Laravel的validateAttribute是受保护方法,无法在自定义规则类外部调用,上述两种方案都是官方推荐的合规替代方式,能准确复用内置规则和自定义规则的验证逻辑。

内容的提问来源于stack exchange,提问作者user4181107

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.01 14:35:39