Problem with embed on a collection of forms of Symfony 4.4

Viewed 316

InvalidPropertyPathException

If I submit the form, without completing the data. I get this error.

Could not parse property path "children[upcomingTours].children[[0]].children[address].children[street].data". Unexpected token "]" at position 36.

Some questions :

  1. Is this a symfony bug? If so, is it already fixed in version 5.x?
  2. Has anyone ever encountered this error?
  3. Does anyone have a solution for this problem?

Thank you in advance for your reply

This is the hierarchy of my form

 - TourType (custom form)
        - UcomingTour (CollectionType)
             - AddressType (custom form)

HTLM

<div>
<label for="tour_upcomingTours_0_address_street">Adresse</label>
<input type="text" 
       id="tour_upcomingTours_0_address_street" 
       name="tour[upcomingTours][0][address][street]" 
       placeholder="Tapez un nom de rue">
</div>

TourType

class TourType extends AbstractType
{
    public function buildForm(FormBuilderInterface $builder, array $options)
    {
        $builder
            ......
            ->add('upcomingTours', CollectionType::class, [
                'label' => false,
                'entry_type' => UpcomingTourType::class,
                'allow_delete' => true,
                'allow_add' => true,
                'by_reference' => false,
            ])
        ;
    }
}

UpcomingTourType

class UpcomingTourType extends AbstractType
{
    public function buildForm(FormBuilderInterface $builder, array $options)
    {
        $builder
             .........
             ->add('address', AddressType::class, [
                    'label' => false,
             ])
    }

}

AddressType

class AddressType extends AbstractType
{
    public function buildForm(FormBuilderInterface $builder, array $options)
    {
        $builder
            ............
            ->add('street', null, [
                'required' => false,
                'label' => 'admin.address_line',
                'attr' => [ 'placeholder' => 'admin.placeholder_line'],
                'constraints' => [
                    new NotNull([
                        'message' => 'project.street_not_blank',
                    ])
                ]
            ])
           
        ;
    }
}

TourController

class TourController extends AbstractController
{
    /**
     * @Route("/tour/new/", name="dashboard_tour_new", methods={"GET","POST"},
     *          defaults={"_locale" = "%locale%"},
     *          requirements={"_locale" = "%app_locales%"})
     */
    public function new(Request $request): Response
    {
        $tour = new Tour();
        $upcomingTour = new UpcomingTour();
        $tour->getUpcomingTours()->add($upcomingTour);
        $form = $this->createForm(TourType::class, $tour);
        $form->handleRequest($request);
        ...

    }
}
2 Answers

I have found the solution.

Problem

The origin of the problem is the validation of the constraints on the form. Symfony collectionType encounters a problem when trying to map the Address form

Solution

The solution is the following:

  • I remove the valuation of the contrants in the form and put it in the entity.

I delete this code:

'constraints' => [
    new NotNull([
          'message' => 'project.street_not_blank',
       ])
 ]

AddressType

class AddressType extends AbstractType
{
    public function buildForm(FormBuilderInterface $builder, array $options)
    {
        $builder
            ............
            ->add('street', null, [
                'required' => false,
                'label' => 'admin.address_line',
                'attr' => [ 'placeholder' => 'admin.placeholder_line'],
            ])
           
        ;
    }
}

Then I put it in the entity

Entity Address

class Address extends BaseEntity
{
    /**
     * @ORM\Id()
     * @ORM\GeneratedValue()
     * @ORM\Column(type="integer")
     */
    protected $id;


    /**
     * @ORM\Column(type="string", nullable=true)
     * @Assert\NotBlank(message="project.street_not_blank")
     */
    private $street;

}

Conclusion

I think it's a symfony bug, for me it will have to support the two method

try to delete the following lines from the controller

$upcomingTour = new UpcomingTour();
$tour->getUpcomingTours()->add($upcomingTour);

or wrap these lines in if ($request->isMethod(Request::METHOD_GET))

Related