Symfony2: выбор вариантов с помощью ajax и проверки

Сценарий: У меня есть форма с двумя выборами. Когда пользователь выбирает что-то из первого выбора, второй выбор заполняется новыми значениями. Эта часть работает нормально.

Но форма не проверяется, так как она содержит некоторые варианты, которые не допускаются в исходной форме.

Форма:

<?php class MyType extends AbstractType { private $category; public function __construct($category = null) { $this->category = $category; } public function buildForm(FormBuilderInterface $builder, array $options) { $builder->add('category', 'choice', array( 'choices' => array( 'foo' => 'foo', 'bar' => 'bar' ) ); $builder->add('template', 'choice', array( 'choices' => $this->loadChoices() ); } private function loadChoices() { // load them from DB depending on the $this->category } } 

Первоначально категория foo . Таким образом, шаблоны для foo загружаются и устанавливаются как выбор. Но если пользователь выбирает bar , шаблоны шаблонов загружаются. Но форма все еще имеет выбор foo и не подтверждает.

Каков наилучший способ решить эту проблему?

Один из способов, который я нашел, – это просто повторить форму в контроллере:

 <?php $form = $this->createForm(new MyType()); if ($request->getMethod() === 'POST') { if ($request->request->has($form->getName()) && isset($request->request->get($form->getName())['category'])) { $form = $this->createForm(new MyType($request->request->get($form->getName())['category'])); } // ... } 

Это работает, но я не могу проверить его, потому что он выбрасывает IllegalArgumentException при установке значения и просто принимает значение по умолчанию. Есть ли лучшее решение для этого? Заранее спасибо!

Solutions Collecting From Web of "Symfony2: выбор вариантов с помощью ajax и проверки"

Я думаю, вам нужно использовать Events для управления этим, что является более правильным способом

 public function buildForm(FormBuilderInterface $builder, array $options) { $builder->add('category', 'choice', array( 'choices' => array( 'foo' => 'foo', 'bar' => 'bar' ) )); $ff = $builder->getFormFactory(); // function to add 'template' choice field dynamically $func = function (FormEvent $e) use ($ff) { $data = $e->getData(); $form = $e->getForm(); if ($form->has('template')) { $form->remove('template'); } $cat = isset($data['category'])?$data['category']:null; // here u can populate ur choices in a manner u do it in loadChoices $choices = array('1' => '1', '2' => '2'); if ($cat == 'bar') { $choices = array('3' => '3', '4' => '4'); } $form->add($ff->createNamed('template', 'choice', null, compact('choices'))); }; // Register the function above as EventListener on PreSet and PreBind $builder->addEventListener(FormEvents::PRE_SET_DATA, $func); $builder->addEventListener(FormEvents::PRE_BIND, $func); }