没有实体的叠层形式的形式集合从不验证
Form collection of imbricated form without entity never validates
我目前正在开发 "Filters" 表单,以增加用户在项目列表上应用过滤器的可能性。我面临的问题是,一旦提交了表单,控制器就认为该表单为空且无效。
转储 $form->getData() 返回的内容显示如下:
array(1) { ["filters"]=> array(0) { } }
日志中既没有错误也没有警告。 GUI returns 过滤器字段错误:
This value is not valid.
但是,如果我修改 Twig 小部件以将 select 的 ID 更改为其他任何内容,我将不再获得无效值,但表单的数据仍然是一个空数组。
这是这个项目的布局:
- 一个包含一个 select 输入和一个文本输入的 FormType,
- 另一种在集合中实现前者的 FormType,
- 实例化并使用表单的控制器,
- 第二个 FormType 的 Twig 视图,
- 和最终的 Twig 页面
FilterSearchType.php
namespace NetDev\CoreBundle\Form\Helpers;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\OptionsResolver\OptionsResolverInterface;
use Symfony\Component\Form\FormBuilderInterface;
use NetDev\CoreBundle\Form\Helpers\FilterType;
class FilterSearchType extends AbstractType {
public function buildForm(FormBuilderInterface $builder, array $options) {
$builder
->add('filters', 'collection', array('type' => new FilterType($options['entity']), 'allow_add' => true,
'allow_delete' => true, 'by_reference' => false))
->add('search', 'submit');
}
public function setDefaultOptions(OptionsResolverInterface $resolver) {
$resolver->setDefaults(array('filters' => [],
'entity' => null));
}
public function getName() {
return 'search_filter';
}
}
FilterType.php
<?php
namespace NetDev\CoreBundle\Form\Helpers;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\OptionsResolver\OptionsResolverInterface;
use Symfony\Component\Form\FormBuilderInterface;
class FilterType extends AbstractType {
public function __construct($entity) {
$this->model = $entity;
}
public function buildForm(FormBuilderInterface $builder, array $options) {
$builder
/*getFilters returns something like that:
* ['Column A' => 'column_a', 'Column B' => 'column_b', ...]
*/
->add('column_name', 'choice', array('choices' => $this->model->getFilters(true)))
->add('search_value', 'text')
;
}
public function setDefaultOptions(OptionsResolverInterface $resolver) {
$resolver->setDefaults(['column_name' => '',
'search_value' => '']);
}
public function getName() {
return 'netdev_filter';
}
}
下面是从控制器向 Twig 提供表单的方式:
RoutesController.php
class RoutesController extends Controller {
public function indexAction($page = 1, Request $request) {
$em = $this->getDoctrine()->getManager();
$orderBy = $request->query->get('orderBy');
$orderType = $request->query->get('orderType');
$form = $this->createForm(new RouteManagerType($em), null, array('orderBy' => $orderBy,
'orderType' => $orderType));
$filterForm = $this->createForm(new FilterSearchType(), null, array('entity' => new Route()));
if ($request->isMethod('POST') && $filterForm->handleRequest($request)->isValid()) {
// Never reached, $filterForm is always marked as invalid
$formData = $filterForm->getData();
var_dump($formData);
exit();
if (!empty($formData['filters']) && count($formData['filters'])) {
if (empty($formData['action'])) $formData['action'] = 'filter';
$form = $this->createForm(new RouteManagerType($em), null,
array('orderBy' => $orderBy,
'orderType' => $orderType,
'filters' => $formData['filters']));
}
}
Twig 小部件:filter_search.html.twig
{% block netdev_filter_widget %}
{% spaceless %}
{{ form_errors(form) }}
<div class="form-group">
<div class="input-group">
<select {{ block('widget_attributes') }} class="form-control" id="search_column">
{% for group_label, choice in form.column_name.vars.choices %}
<option value="{{ choice.value }}" {{ block('attributes') }}>{{ choice.label }}</option>
{% endfor %}
</select>
<div class="input-group-addon">contains</div>
<input type="text" class="form-control" id="search_criteria" placeholder="search"/>
</div>
</div>
{% endspaceless %}
{% endblock %}
我几乎倾尽所有,但没有什么是真正有趣的。我什至不确定内核是否理解/正确 "links" 用户执行的提交以及控制器创建的表单。
如有任何帮助,我们将不胜感激。
好的,所以问题是如果你自己渲染,你应该非常清楚 HTML 中渲染的名称正是后端所期望的,否则你会遇到这样的问题。
解决这个问题的最佳方法是以默认表单呈现为起点,在您完全确定需要自定义模板之前不要进行任何自定义 HTML。当你这样做时,检查默认模板以查看元素的名称是如何构建的,并遵循完全相同的命名,或者更好的是,尽可能重用基本模板(通过扩展块和调用 parent() and/or使用 block
函数)。
我目前正在开发 "Filters" 表单,以增加用户在项目列表上应用过滤器的可能性。我面临的问题是,一旦提交了表单,控制器就认为该表单为空且无效。
转储 $form->getData() 返回的内容显示如下:
array(1) { ["filters"]=> array(0) { } }
日志中既没有错误也没有警告。 GUI returns 过滤器字段错误:
This value is not valid.
但是,如果我修改 Twig 小部件以将 select 的 ID 更改为其他任何内容,我将不再获得无效值,但表单的数据仍然是一个空数组。
这是这个项目的布局:
- 一个包含一个 select 输入和一个文本输入的 FormType,
- 另一种在集合中实现前者的 FormType,
- 实例化并使用表单的控制器,
- 第二个 FormType 的 Twig 视图,
- 和最终的 Twig 页面
FilterSearchType.php
namespace NetDev\CoreBundle\Form\Helpers;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\OptionsResolver\OptionsResolverInterface;
use Symfony\Component\Form\FormBuilderInterface;
use NetDev\CoreBundle\Form\Helpers\FilterType;
class FilterSearchType extends AbstractType {
public function buildForm(FormBuilderInterface $builder, array $options) {
$builder
->add('filters', 'collection', array('type' => new FilterType($options['entity']), 'allow_add' => true,
'allow_delete' => true, 'by_reference' => false))
->add('search', 'submit');
}
public function setDefaultOptions(OptionsResolverInterface $resolver) {
$resolver->setDefaults(array('filters' => [],
'entity' => null));
}
public function getName() {
return 'search_filter';
}
}
FilterType.php
<?php
namespace NetDev\CoreBundle\Form\Helpers;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\OptionsResolver\OptionsResolverInterface;
use Symfony\Component\Form\FormBuilderInterface;
class FilterType extends AbstractType {
public function __construct($entity) {
$this->model = $entity;
}
public function buildForm(FormBuilderInterface $builder, array $options) {
$builder
/*getFilters returns something like that:
* ['Column A' => 'column_a', 'Column B' => 'column_b', ...]
*/
->add('column_name', 'choice', array('choices' => $this->model->getFilters(true)))
->add('search_value', 'text')
;
}
public function setDefaultOptions(OptionsResolverInterface $resolver) {
$resolver->setDefaults(['column_name' => '',
'search_value' => '']);
}
public function getName() {
return 'netdev_filter';
}
}
下面是从控制器向 Twig 提供表单的方式:
RoutesController.php
class RoutesController extends Controller {
public function indexAction($page = 1, Request $request) {
$em = $this->getDoctrine()->getManager();
$orderBy = $request->query->get('orderBy');
$orderType = $request->query->get('orderType');
$form = $this->createForm(new RouteManagerType($em), null, array('orderBy' => $orderBy,
'orderType' => $orderType));
$filterForm = $this->createForm(new FilterSearchType(), null, array('entity' => new Route()));
if ($request->isMethod('POST') && $filterForm->handleRequest($request)->isValid()) {
// Never reached, $filterForm is always marked as invalid
$formData = $filterForm->getData();
var_dump($formData);
exit();
if (!empty($formData['filters']) && count($formData['filters'])) {
if (empty($formData['action'])) $formData['action'] = 'filter';
$form = $this->createForm(new RouteManagerType($em), null,
array('orderBy' => $orderBy,
'orderType' => $orderType,
'filters' => $formData['filters']));
}
}
Twig 小部件:filter_search.html.twig
{% block netdev_filter_widget %}
{% spaceless %}
{{ form_errors(form) }}
<div class="form-group">
<div class="input-group">
<select {{ block('widget_attributes') }} class="form-control" id="search_column">
{% for group_label, choice in form.column_name.vars.choices %}
<option value="{{ choice.value }}" {{ block('attributes') }}>{{ choice.label }}</option>
{% endfor %}
</select>
<div class="input-group-addon">contains</div>
<input type="text" class="form-control" id="search_criteria" placeholder="search"/>
</div>
</div>
{% endspaceless %}
{% endblock %}
我几乎倾尽所有,但没有什么是真正有趣的。我什至不确定内核是否理解/正确 "links" 用户执行的提交以及控制器创建的表单。
如有任何帮助,我们将不胜感激。
好的,所以问题是如果你自己渲染,你应该非常清楚 HTML 中渲染的名称正是后端所期望的,否则你会遇到这样的问题。
解决这个问题的最佳方法是以默认表单呈现为起点,在您完全确定需要自定义模板之前不要进行任何自定义 HTML。当你这样做时,检查默认模板以查看元素的名称是如何构建的,并遵循完全相同的命名,或者更好的是,尽可能重用基本模板(通过扩展块和调用 parent() and/or使用 block
函数)。