Php Symfony 2-如何将数据传递给formBuilder?
我正在表单中使用实体选择列表。我只想使用特定的实体(例如:仅用户所属的组) 所以,在控制器中,我获取这些组,并尝试将它们传递到Php Symfony 2-如何将数据传递给formBuilder?,php,symfony,formbuilder,Php,Symfony,Formbuilder,我正在表单中使用实体选择列表。我只想使用特定的实体(例如:仅用户所属的组) 所以,在控制器中,我获取这些组,并尝试将它们传递到formBuider 控制器: /.../ $groups = $em->getRepository('VendorMyBundle:Group')->getUserGroups($user); $form = $this->createForm(new Message($groups), $message); /.../ 那么,现在怎么办?如何在fo
formBuider
控制器:
/.../
$groups = $em->getRepository('VendorMyBundle:Group')->getUserGroups($user);
$form = $this->createForm(new Message($groups), $message);
/.../
那么,现在怎么办?如何在formBuilder中使用它?
如何将此行更改为使用已传递的组数组
->add('group','entity',array('class' => 'Vendor\MyBundle\Entity\Group', 'label'=>'Group:'))
或者以另一种方式:
class MessageType
{
/.../
public function buildForm(FormBuilder $builder, array $options)
{
$builder
->add('group','entity',
array(
'class' => 'Vendor\MyBundle\Entity\Group',
'property' => 'name',
'query_builder' => function ($repository) {
$qb = $repository->createQueryBuilder('group');
$qb->add('where', 'group.administrator = :user');
$qb->setParameter('user', $user->getId());
return $qb;
},
'label' => 'Group'
)
)
// Continue adding fields
;
}
/.../
}
那么,如何才能在form builder中获得要使用的对象$user?($user代表当前登录的用户)如果要使用自定义查询,必须按如下方式设置
query\u builder
选项:
use Doctrine\ORM\EntityRepository;
...
$message = new Message();
$form = $this->createFormBuilder($message)
->add('group', 'entity', array(
'class' => 'Vendor\MyBundle\Entity\Group',
'label'=>'Group:',
'query_builder' => function(EntityRepository $er) {
return $er->createQueryBuilder('g')
->... // whatever you want to do
}
))
->getForm();
您可以在中找到有关查询生成器的详细信息以及中的
实体的选项。您可以在_construct()方法中提供要使用的对象
例如:
在您的表单类型中:
function __construct(\Your\Bundle\Entity\Company $company, \DYB\ConnectBundle\Entity\Ad $ad) {
$this->company = $company;
$this->ad = $ad;
}
然后在表单中键入buildForm方法:
$company = $this->company;
$builder->add('ad', 'entity', array(
'class' => '\Your\Bundle\Entity\Ad',
'query_builder' => function(\Your\Bundle\Repository\AdRepository $er) use ($company) {
return $er->getActiveAdsQueryBuilder($company);
},
));
细菌的解决方案真的很好。只是给像我这样的人留个便条,省得他们头疼:)
在这一部分中,我想指出使用($company)
部分。
它被框架隐藏了起来,当然没有它任何东西都不能正常工作
$builder->add('ad', 'entity', array(
'class' =>
'\Your\Bundle\Entity\Ad',
'query_builder' =>
function(\Your\Bundle\Repository\AdRepository $er) use ($company) {
return $er->getActiveAdsQueryBuilder($company);
},
)
);
最好的方法(我的意见)是给你的表单实体管理器,并选择所有你需要的。但不要忘记在setDefaults()中声明空键,否则数据将不会传递给构建器
像这样的
public function buildForm(FormBuilderInterface $builder, array $options)
{
$options['em']->getRepository(''); // select all you need
$builder->add('title', 'text')
->add('content', 'textarea');
}
public function setDefaultOptions(OptionsResolverInterface $resolver)
{
$resolver->setDefaults(array(
'data_class' => 'Main\BlogBundle\Entity\Post',
'validation_groups' => array('post'),
'required' => false,
'em' => null // this var is for your entityManager
));
}
将EM作为简单选项应用 细菌的溶液不是好的。例如,如果将类型声明为服务,则不可能将对象传递给构造函数
//In controller pass the value which you want to use in builder form in array like
$object = new Question();
$form->create(new QuestionType() , $object , array('sqtname'=>2,'question_type'=>2));
//In Form type class
public function buildForm(FormBuilderInterface $builder , array $options)
{
//for setting data field dynamically
if (array_key_exists('question_type', $options) && $options['question_type'] != '') {
$data = $em->getReference("RecrutOnlineStandardBundle:StdQuestionType",$options['question_type']->getId());
} else {
$data = "";
}
$builder->add('StdQuestionType', 'entity', array(
'class' => 'TestStandardBundle:StdQuestionType',
'property' => 'name',
'empty_value' => 'Sélectionner un question type',
'required' => true,
'data' => $data,
'query_builder' => function(EntityRepository $er ) use ( $options ) {
if (isset($options['sqtname']) && $options['sqtname'] != '') {
return $er->createQueryBuilder('sqt')
->where("sqt.name!= ".$options['sqtname']);
} else{
return $er->createQueryBuilder('sqt');
}
}
));
}
public function setDefaultOptions(OptionsResolverInterface $resolver)
{
$resolver->setDefaults(array(
'data_class' => 'Test\QuestionBundle\Entity\Question',
'required' => false,
'sqtname' => '',
'question_type' =>''
));
}
一个完美的解决方案是选项—只需将数据作为选项传递给form builder。是的,我知道如何使用自定义查询,但当我想要获取当前登录用户组时,如何使用它?我必须在表单类型类中声明容器?例如:在控制器im中使用$this->get('security.context')->getToken()->getUser()
我建议在这里使用manytone或manytomy关系。这会让事情变得更简单。你可以在类型类中创建构造函数,只需在控制器中推送安全上下文变量即可。我问了同样的问题:-细菌的解决方案真的很好!!!:thumbsup:如果您需要执行查询、进行api调用等来呈现视图,那么您就错了。如果这是symfony在框架上设置的约束(没有其他方法向表单生成器提供任意数据),那么他们就太丢脸了。这是控制器明确定义的工作。此外,他的解决方案将在3.0中突破,因为类型是由FQCNC构造的。但这不违背MVC应用程序的目的吗?我认为框架的全部意义在于将数据层与渲染层混为一谈。尽可能地。Symfony2会破坏你知道的所有模式。。。所以不要感到奇怪。我展示了一个对我有用的解决方案,如果您想使用模式,sf2对于开发来说是一个糟糕的mvc。如果你有更优雅的-用你的…现在这个答案是错误的。您应该将这些参数作为选项传递(在配置选项
方法中定义),而不是在类型
的\u构造
中。类型
在容器中构造一次,因此如果在容器中传递参数,并且在同一个请求中多次使用类型
,并且在\u构造
中使用不同的参数,则会出现奇怪的行为:在容器中,您应该只使用autowire服务。
//In controller pass the value which you want to use in builder form in array like
$object = new Question();
$form->create(new QuestionType() , $object , array('sqtname'=>2,'question_type'=>2));
//In Form type class
public function buildForm(FormBuilderInterface $builder , array $options)
{
//for setting data field dynamically
if (array_key_exists('question_type', $options) && $options['question_type'] != '') {
$data = $em->getReference("RecrutOnlineStandardBundle:StdQuestionType",$options['question_type']->getId());
} else {
$data = "";
}
$builder->add('StdQuestionType', 'entity', array(
'class' => 'TestStandardBundle:StdQuestionType',
'property' => 'name',
'empty_value' => 'Sélectionner un question type',
'required' => true,
'data' => $data,
'query_builder' => function(EntityRepository $er ) use ( $options ) {
if (isset($options['sqtname']) && $options['sqtname'] != '') {
return $er->createQueryBuilder('sqt')
->where("sqt.name!= ".$options['sqtname']);
} else{
return $er->createQueryBuilder('sqt');
}
}
));
}
public function setDefaultOptions(OptionsResolverInterface $resolver)
{
$resolver->setDefaults(array(
'data_class' => 'Test\QuestionBundle\Entity\Question',
'required' => false,
'sqtname' => '',
'question_type' =>''
));
}