Symfony ValidatorComponent > AnnotationMapping in FormComponent

286 views Asked by At

Im working on a project where I'm using some Symfony Components. My problem is how to make the Form Component's validation of Forms use AnnotationMapping to find the constraints.

SetUp:

global $loader; //composer - autoload
AnnotationRegistry::registerLoader([$loader, 'loadClass']);

$validator = Validation::createValidatorBuilder()
    ->enableAnnotationMapping()
    ->getValidator();

$formFactory = Forms::createFormFactoryBuilder()
    [...]
    ->addExtension(new ValidatorExtension($validator))
    ->getFormFactory();

Entity

/**
 * @ORM\Entity
 * @ORM\Table(name="..")
 */
class Conductor extends AbstractEntity {

    /**
     * @ORM\Id
     * @ORM\Column(type="integer")
     * @ORM\GeneratedValue
     */
    protected $id;

    /**
     * @Assert\NotBlank()
     * @ORM\Column(type="string")
     */
    protected $pattern;

[...]

}

Building the Form


$builder = $App->getFormFactory()->createBuilder(FormType::class, $entity_data);
foreach ($fields as $field) {
    $builder->add(
        $field,
        null,
        [
            "attr" => array("class" => "..."),
        ]
    );
}
$builder->getForm();

FormSubmit / Validation


if($request->isMethod('POST')) {
            
    $formTable = $this->createFormTable( array() );
    $form = $formTable->buildForm($entity);
    $form->submit($this->dataMapper->formDataFromPost());

    /*
    $entity = $this->dataMapper->mapFromPost();
    $validator = Validation::createValidatorBuilder()
      ->enableAnnotationMapping()
      ->getValidator();
    */


    if($form->isValid()) {
        [...]
    } else {
        [...]
    }
}

Im trying to make the NotBlank() Constraints work. But my form passes the validation in any case. If I use a new validator and validate with it, it will show me the correct Errors. But the Form->isValid() function does not. Maybe it is not configured correctly to use AnnotationMapping? Thank you very much in advance for tipps or solutions!

Problem localization

The form handleRequest / submit and validation are working as expected!

The form does not have any constraints!! -> Mapping the Constraints from Annotation is not happening / working.

I did find a similar question: Why does Symfony form not validate my DTO with constraint annotations?

1

There are 1 answers

0
Martin On

I wasn't able to find a solution to enable the mapping that should happen inside the FormComponent with the ValidatorExtension.

But I did find a functional workaround. My approach is to get the Constraints from the readPropertyMetadata function of the validator:


use Symfony\Component\Validator\Validation;



public function buildForm(AbstractEntity $entity) {

    $validator = Validation::createValidatorBuilder()
        ->enableAnnotationMapping()
        ->getValidator();

    $fields = [*ENTITY PRPERTIES*];

    $classMeta = $validator->getMetadataFor($entity);

    foreach ($fields as $field) {
        $metadata = $classMeta->getPropertyMetadata($field);
        if(is_array($metadata) && count($metadata) > 0) {
            $constraints = $classMeta->getPropertyMetadata($field)[0]->constraints;
        } else {
            $constraints = [];
        }
            

        $builder->add(
            $field,
            null,
            [
                "attr" => array("class" => "..."),
                "constraints" => $constraints
            ]
        );
    }
}

As now the constraints are added to the form the validation finally works as expected.