skip to Main Content

I am trying to add a Choice Constraint inside one of my forms.

This below is one of my fields. I have an entity that holds some roles and I want to be able to choose multiple roles in my form. I wanted to add the constraints for all of my fields and decided to do it here in the FormType, but I tried doing it using Assert inside the Entity as well, and I got the same error.

$builder->
    ->add('admin_role', EntityType::class, [
         'class' => UserAdminRole::class,
         'choice_label' => 'public_name',
         'query_builder' => function(EntityRepository $er){
             return $er->createQueryBuilder('r')
                        ->andWhere('r.role_type = :paramRoleType')
                        ->setParameter('paramRoleType', 'personal');
             },
         'multiple' => true,
         'expanded' => true,
         'label' => 'Functie',
         'constraints' => new Choice(
              callback: [UserAdminRole::class, 'getPersonalRoles'], //this line causes the error
              min: 1,
              // max: 1,
              minMessage: $choiceMinMessage,
              // maxMessage: $maxMessage,
            )
        ]);

The callback parameter expects callable|string inside the Choice Constraint class (image below). And I passed an array with the Entity in which I have the getPersonalRoles method, but the docs guide me to define an array in case I have a method in another Entity.

Choice Constraint class

Symfony Docs mentions array as available type

Symfony’s docs

This is the error I am getting :

the error im getting

I tried following the docs and added an array in which I specified my callback that lives inside another Entity.

The callback parameter states that it expects only a string or callable, so are the docs wrong or am I missing something?

Also how can I add this constraint otherwise?

2

Answers


  1. I don’t think that is a symfony problem. The thing is that php is tricky here.

    Look at this output:

    class Test
    {
        public function a() {
    
        }
    
        public static function b() {
    
        }
    }
    
    var_dump(is_callable([Test::class, 'a'])); // false
    var_dump(is_callable([Test::class, 'b'])); // true
    

    An array can be callable if it contains two strings. The first is the class and the second must be a static function.

    So getPersonalRoles should be static!

    Login or Signup to reply.
  2. I believe you are mixing up to concepts as it is mentioned
    in documentation

    If the callback is defined in a different class and is static, for
    example AppEntityGenre, you can pass the class name and the method
    as an array

    If considering above scenario first of all your method must be static secondly

    $metadata->addPropertyConstraint('genre', new AssertChoice([
            'callback' => [Genre::class, 'getGenres'],
        ]));
    

    As mentioned in code if you are trying to call callback as an array in Choice you have to use like an array in you case it could be

    new AssertChoice([
              callback => [UserAdminRole::class, 'getPersonalRoles'],
            ])
    

    I would recommend you go through again from the documentation

    https://symfony.com/doc/current/reference/constraints/Choice.html#choices

    'constraints' => [
        new Choice([
            'callback' => [UserAdminRole::class, 'getPersonalRoles'],
        ]),
    
    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search