Register a custom dependent validator extension.

@param  string  $rule
@param  \Closure|string  $extension
@return void
177879
public function addDependentExtension($rule, $extension)
    {
        $this->addExtension($rule, $extension);

        $this->dependentRules[] = Str::studly($rule);
    }
142742
public function add(\Caridea\Validate\Rule ...$rules): self
    {
        $this->rules = array_merge($this->rules, $rules);
        return $this;
    }
645061
public function setRule(Rule $rule)
    {
        $expectedType = $this->getRuleType();
        
        if (Reflection::isInstanceOf($rule, $expectedType) === true) {
            $this->rule = $rule;
        } else {
            $procClass = get_class($this);
            $givenType = get_class($rule);
            $msg = "The ${procClass} Rule Processor only processes ${expectedType} Rule objects, ${givenType} given.";
            throw new InvalidArgumentException($msg);
        }
    }
37643
public function getFilterForRule(Rule $rule)
    {
        $filterIdentifier = $rule->getFilter();

        if (class_exists($filterIdentifier)) {
            return new $filterIdentifier;
        }

        $error = "Unable to locate filter for: $filterIdentifier defined in " . get_class($rule);
        throw new \UnexpectedValueException($error);
    }
648454
protected function applyRule($fields, array $rule, array $onlyChecked)
    {
        $fields    = \is_string($fields) ? Filters::explode($fields) : (array)$fields;
        $validator = \array_shift($rule);

        // How to determine the property is empty(default use the Validators::isEmpty)
        $isEmpty = [Validators::class, 'isEmpty'];
        if (!empty($rule['isEmpty']) && (\is_string($rule['isEmpty']) || $rule['isEmpty'] instanceof \Closure)) {
            $isEmpty = $rule['isEmpty'];
        }

        // Preconditions for verification -- If do not meet the conditions, skip this rule
        $when = $rule['when'] ?? null;
        if ($when && ($when instanceof \Closure) && $when($this->data, $this) !== true) {
            return;
        }

        // Whether to skip when empty(When not required). ref yii2
        $skipOnEmpty = $rule['skipOnEmpty'] ?? $this->_skipOnEmpty;
        $filters     = $rule['filter'] ?? null;  // filter
        $defMsg      = $rule['msg'] ?? null; // Custom error message
        $defValue    = $rule['default'] ?? null;// Allow default

        // clear all keywords options. 0 is the validator
        unset($rule['msg'], $rule['default'], $rule['skipOnEmpty'], $rule['isEmpty'], $rule['when'], $rule['filter']);

        // The rest are validator parameters. Some validators require parameters. e.g. size()
        $args = $rule;

        foreach ($fields as $field) {
            if (!$field || ($onlyChecked && !\in_array($field, $onlyChecked, true))) {
                continue;
            }

            $value = $this->getByPath($field, $defValue);

            if (\is_string($validator)) {
                if ($validator === 'safe') {
                    $this->setSafe($field, $value);
                    continue;
                }

                // required*系列字段检查 || 文件资源检查
                if (self::isCheckRequired($validator) || self::isCheckFile($validator)) {
                    $result = $this->fieldValidate($field, $value, $validator, $args, $defMsg);

                    if (false === $result && $this->isStopOnError()) {
                        break;
                    }
                    continue;
                }
            }

            // skip On Empty && The value is empty
            if ($skipOnEmpty && Helper::call($isEmpty, $value)) {
                continue;
            }

            // Field value filtering(有通配符`*`的字段, 不应用过滤器)
            if ($filters && !\strpos($field, '.*')) {
                $value = $this->valueFiltering($value, $filters);
                // save
                $this->data[$field] = $value;
            }

            // Field value verification check
            if (!$this->valueValidate($field, $value, $validator, $args, $defMsg) && $this->isStopOnError()) {
                break;
            }
        }
    }
1083008
public function rule($rule, $field)
    {
        $ruleMethod = 'is' . ucfirst($rule);
        if (!isset(static::$rules[$rule]) && !method_exists($this, $ruleMethod)) {
            throw new \InvalidArgumentException(Lang::get('_NOT_FOUND_', 'validate rule [' . $rule . ']'));
        }

        $params = array_slice(func_get_args(), 2);

        $this->dateBindRule[] = [
            'rule' => $rule,
            'field' => (array)$field,
            'params' => (array)$params
        ];
        return $this;
    }
754409
public function addDependentExtensions(array $extensions)
    {
        $this->addExtensions($extensions);

        foreach ($extensions as $rule => $extension) {
            $this->dependentRules[] = Str::studly($rule);
        }
    }
34710
public function addRule(ValidatorRule $rule, $field, $flags = 0x00000) {
    $key = $this->getKey($field);
    $this->rules[$key][] = $rule;
    
    if ($rule instanceof FieldValidatorRule) {
      $rule->setField($field);
    }
    
    if ($flags & self::OPTIONAL) {
      $this->setOptional($field);
    }
  }
666752
private function setupRules($rules)
    {
        // prepares filter for requiredIf
        $rules = Utils\HelperRequiredIf::prepare($this, $rules);

        // prepares filter for sameWith.
        $rules = Utils\HelperSameWith::prepare($this, $rules);

        return $rules;
    }
269101
public function validateRule($type, $rule)
    {
        $requiredParams = call_user_func(__NAMESPACE__ . "\\" . $type . "::GetRequiredParams", $rule);
        // check if rule is valid
        if ($requiredParams == null && !is_array($requiredParams))
        {
            throw new Exceptions\OntraportAPIException($rule . " is not a valid rule type.");
        }
        // validate rule is used for correct object
        if (call_user_func(__NAMESPACE__ . "\\" . $type . "::CheckRestricted", $rule) && ($this->_object_type_id != 0))
        {
            throw new Exceptions\OntraportAPIException($rule . " can only be used with Contacts object.");
        }
        return true;
    }
362190
public function apply(Rule $rule, $value)
    {
        $type = $rule->getInputType();

        if ($type == CallbackRule::SELF_METHOD_TYPE) {
            return $this->useObjectMethod($rule->callback, $value);
        }

        if ($type == CallbackRule::CALLABLE_TYPE) {
            return $this->useCallable($rule->callback, $value);
        }

        if ($type == CallbackRule::CLOSURE_TYPE) {
            return $this->useClosure($rule->callback, $value);
        }

        throw new InvalidCallbackException("Unsupported callback provided, failed to filter property");
    }
679424
protected function checkRuleCorrect($rule)
    {
        if (!isset($rule->value)) {
            // We will assume a missing value for the rule is to be interpreted as empty.
            $rule->value = null;
        }
        if (!isset($rule->id, $rule->field, $rule->type, $rule->input, $rule->operator)) {
            return false;
        }
        if (!isset($this->operators[$rule->operator])) {
            return false;
        }

        return true;
    }
694017
public function isApplicableTo(Rule $rule)
    {
        $userTypes = Rule::getUserTypes();

        return (null !== $rule->getUser() && Rule::RECEIVER_USER === $userTypes[$rule->getUserType()]);
    }
549129
private function ruleTemplate($rule)
    {
        $file = __DIR__ . "/../templates/validator/rule.php.dist";

        if (file_exists($file))
        {
            $template = strtr(file_get_contents($file), [
                '{{namespace}}' => get_app_namespace(),
                '{{rule}}' => $rule
            ]);

            if (!file_exists(app_path("Validation/Rules")))
            {
                mkdir(app_path("Validation/Rules"), 0755, true);
            }

            $file_path = app_path("Validation/Rules/{$rule}.php");

            $file = fopen($file_path, "w");
            fwrite($file, $template);
            fclose($file);

            return file_exists($file_path);
        }

        return false;
    }
846123
protected function __checkRule($rule) {
        $fields = explode(',', $rule[0]);
        if (is_string($rule[1])) {
            $conditions = explode(',', $rule[1]);
            foreach ($conditions as $k => $item) {
                $item = trim($item);
                $conditions[$k] = isset($this->aliases[$item]) ? $this->aliases[$item] : $item;
            }
        } else {
            $conditions = array($rule[1]);
        }
        $valid = true;
        foreach ($conditions as $condition) {
            foreach ($fields as $field) {
                $field = trim($field);
                $label = isset($this->labels[$field]) ? $this->labels[$field] : ucwords(str_replace('_', ' ', $field));
                $errorMessage = isset($rule['message']) ? $this->translate(str_replace(array('__VALUE__', '__LABEL__'), array((!is_null($this->getValue($field))) ? $this->getValue($field) : ' - no value -', $label), $rule['message'])) : null;
                if ('required' == $condition && ((is_null($this->getValue($field))) || (is_array($this->getValue($field)) && !count($this->getValue($field))) || (is_string($this->getValue($field)) && '' == trim($this->getValue($field))))) {
                    if (!isset($this->errors[$field])) {
                        $this->errors[$field] = array();
                    }
                    $this->errors[$field][] = $errorMessage ? $errorMessage : $this->translate($label . ' is required!');
                    $valid = false; // if it's required but not defined then the rule it's not valid.
                    continue;
                } elseif (is_null($fieldValue = $this->getValue($field)) || (is_array($fieldValue) ? !count($fieldValue) : !trim($fieldValue))) { // if it's not required and not defined then there is nothing to check
                    if (isset($rule['default_value'])){
                        $this->setValue($field, $rule['default_value']);
                    }
                    continue;
                }
                if ('required' == $condition || 'safe' == $condition) { // skip required as it was checked above also skip safe as it is a model condition and not implemented here
                    continue;
                }
                try {
                    // actually check conditions here (except for required which is an exception from the rule
                    if (is_string($condition)) { // check local condition
                        $valid = $valid && $this->{'filter' . ucwords($condition)}($field, $rule, $label, $errorMessage);
                    } elseif (is_callable($condition)) { // check method condition
                        $valid = $valid && $condition($this, $field, $rule, $label, $errorMessage);
                    }
                } catch (\Exception $e) {
                    $valid = false;
                    if (!isset($this->errors[$field])) {
                        $this->errors[$field] = array();
                    }
                    $this->errors[$field][] = is_array($e) ? $e['message'] : $e->getMessage();
                }
            }
        }
        return $valid;
    }
1235644
public function extend($rule, $extension, $message = null)
    {
        $this->extensions[$rule] = $extension;

        if ($message) {
            $this->fallbackMessages[Str::snake($rule)] = $message;
        }
    }
220644
protected function validate( $attribute, $rule )
	{
		list( $rule, $parameters ) = $this->parseRule( $rule );

		if ( $rule == '' )
		{
			return;
		}

		// First we will get the correct keys for the given attribute in case the field is nested in
		// an array. Then we determine if the given rule accepts other field names as parameters.
		// If so, we will replace any asterisks found in the parameters with the correct keys.
		if ( ( $keys = $this->getExplicitKeys( $attribute ) ) && $this->dependsOnOtherFields( $rule ) )
		{
			$parameters = $this->replaceAsterisksInParameters( $parameters, $keys );
		}

		// We will get the value for the given attribute from the array of data and then
		// verify that the attribute is indeed validatable. Unless the rule implies
		// that the attribute is required, rules are not run for missing values.
		$value = $this->getValue( $attribute );

		$validatable = $this->isValidatable( $rule, $attribute, $value );

		$method = "validate{$rule}";

		if ( $validatable && !$this->$method( $attribute, $value, $parameters, $this ) )
		{
			$this->addFailure( $attribute, $rule, $parameters );
		}
	}