Как красиво остановить проверку свойства объекта при первой ошибке в Symfony? - PullRequest
0 голосов
/ 29 декабря 2018

У меня есть следующий код:


    class User
    {
        /**
         * @Assert\Type(type="string")
         * @Assert\NotBlank()
         * @Assert\Email()
         * @Assert\Length(max=255)
         */
        public $email;
    }

Этот объект заполняется из вызова API.Когда происходит проверка и свойство заполняется значением массива вместо строки, проверки NotBlank, Email и Length продолжают работать, и я получаю «UnexpectedTypeException».

Я хочу, чтобы система проверки добавила только одну ошибку о неправильном значениивведите и остановитесь там.

Я сделал пользовательский валидатор ограничений


    class ChainConstraintValidator extends ConstraintValidator
    {
        /**
         * {@inheritdoc}
         */
        public function validate($value, Constraint $constraint)
        {
            if (!$constraint instanceof ChainConstraint) {
                throw new UnexpectedTypeException($constraint, __NAMESPACE__.'\All');
            }

            $context = $this->context;
            $prevCount = $context->getViolations()->count();
            $validator = $context->getValidator()->inContext($context);

            foreach ($constraint->constraints as $constraintStep) {
                $errors = $validator->validate($value, $constraintStep);

                if ($errors->getViolations()->count() > $prevCount) {
                    break;
                }
            }
        }
    }

Это работает, и я использовал его так:


    @ChainConstraint(
        @Assert\Type(type="string"),
        @Assert\NotBlank(),
        @Assert\Email(),
        @Assert\Length(max=255)
    )
    

У меня многотакие занятия в моем проекте.Есть ли более красивый и требующий меньшего количества кода способ добиться этого?

Ответы [ 2 ]

0 голосов
/ 18 мая 2019

Что по этому поводу:

$var = [];

$constraints = [
 new Type(['type'=>'string', 'groups'=> 'first-check']),
 new NotBlank(['groups'=> 'second-check']),
 new Email(['groups'=> 'second-check']),
 new Length(['min'=>2, 'groups'=> 'second-check'])]
    ;

$groups = ['first-check', 'second-check'];
$groupSequence = new GroupSequence($groups);
$error = $validator->validate($var, $constraints, $groupSequence);

if(count($error) > 0) {
    dd($error); // Contains 1 ConstraintViolation (Type) 
 }
0 голосов
/ 31 декабря 2018

В этих проблемах вы можете найти некоторую информацию, которая, по-видимому, похожа на поведение, которое вы хотите иметь:

Как описано в этих вопросах, я думаю, что лучший способ сделать это правильно -используйте групповую проверку , даже если это кажется немного неуклюжим, чтобы делать это при каждом утверждении.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...