使用与同一个类相关的一些动态表单

时间:2015-02-26 09:40:11

标签: php forms symfony

Symfony 2.3

我正在嵌入一些Form以便能够更改与权限相关的每个用户属性。我为同一页面中的每个用户创建了一个UserAdminType

<?php

namespace Msalsas\UserAdminBundle\Form;

use Msalsas\UserBundle\Entity\User;
use Msalsas\UserBundle\Entity\ExtendedUser;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\FormBuilderInterface;
use Symfony\Component\OptionsResolver\OptionsResolverInterface;
use Symfony\Component\Form\FormInterface;
use Symfony\Component\Form\FormEvents;
use Symfony\Component\Form\FormEvent;

class UserAdminType extends AbstractType
{
private $user;

public function __construct(User $user)
{
    $this->user = $user;
    $this->extendedUser = new ExtendedUser($this->user);
}

/**
 * @param FormBuilderInterface $builder
 * @param array $options
 */
public function buildForm(FormBuilderInterface $builder, array $options)
{

    $extendedUser = $this->extendedUser;

    $builder
        ->add('extendedRole',
            'choice', array('choices' => array(
                $extendedUser::ROLE_1 => "Role 1",
                $extendedUser::ROLE_2 => "Role 2",
                $extendedUser::ROLE_3 => "Role 3",
             ),
            'label' => $this->user->getUsername()
        ))
        ->add('Change roles for '.$this->user->getUsername(), 'submit')
    ;

    $builder->addEventListener(
        FormEvents::POST_SUBMIT,
        function (FormEvent $event) {
            $form = $event->getForm();

            $data = $event->getData();

            if( ! $form->getClickedButton('Change roles for '.$this->user->getUsername()) )
            {
                  // Here I should avoid submitting the form 
            }

        }
    );

}

/**
 * @param OptionsResolverInterface $resolver
 */
public function setDefaultOptions(OptionsResolverInterface $resolver)
{
    $resolver->setDefaults(array(
        'data_class' => 'Msalsas\UserBundle\Entity\ExtendedUser',
        'empty_data' => function (FormInterface $form) {
                return null;
            }
    ));
}

/**
 * @return string
 */
public function getName()
{
    return 'extendedUserRoleForm';
}
}

问题在于,当我提交其中一个表单时,所有其他表单也会被提交,返回错误,因为extendedUser使用构造函数初始化对象User作为参数:

  

捕获致命错误:传递给Msalsas \ UserBundle \ Entity \ ExtendedUser :: __ construct()的参数1必须是Msalsas \ UserBundle \ Entity \ User的实例,没有给出,在... / vendor / symfony / symfony中调用第140行的/src/Symfony/Component/Form/Extension/Core/Type/FormType.php并定义了

我还尝试使用新的默认empty_data设置ExtendedUser

public function setDefaultOptions(OptionsResolverInterface $resolver)
{
    $resolver->setDefaults(array(
        'data_class' => 'Msalsas\UserBundle\Entity\ExtendedUser',
        'empty_data' => function (FormInterface $form) {
                return $this->extendedUser;                    
            }
    ));
}

现在,在提交表单时,新实体会被保留,但其他表单仍然会被提交,并返回错误:This form should not contain extra fields.这似乎是由于重复的属性名称(extendedRole )。

我怎样才能避免提交其他表格?

1 个答案:

答案 0 :(得分:0)

我找到了解决方案here

每个表格必须具有不同的名称。所以我添加了$name属性,并在构造函数中分配了它:

private $user;
private $name = 'default_name_';
private $extendedUser;

public function __construct(User $user, $formName)
{
    $this->user = $user;
    $this->extendedUser = new ExtendedUser($this->user);
    $this->name = $this->name.$formName;
}

//... (No event required)

/**
 * @return string
 */
public function getName()
{
    return $this->name;
}

$formName参数与当前用户相关。通过这种方式,只有&#34;点击&#34;表格已提交。希望它有所帮助。