我正在尝试将具有值的数组提交到symfony 4表单字段,但是验证一直失败。
我正在将应用程序从symfony 2.7更新到symfony4。问题在于,由于symfony格式的更改,我现在使用的表单始终无法通过验证。
symfony表单具有以下字段
$builder->add('contactData', null, ['mapped' => false])
在symfony 2.7中,我将始终在contactData
字段中提交具有数组值的POST请求,由于未映射它,因此它将在提交过程中将数据设置为字段对象,并且在处理程序。请求示例:
{
"name": {
"aField": "aValue",
"contactData": {
"something": "value"
}
}
}
但是在symfony 4中,\Symfony\Component\Form\Form
类中现在增加了验证检查
} elseif (\is_array($submittedData) && !$this->config->getCompound() && !$this->config->hasOption('multiple')) {
,这会导致在将数据提交到contactData
字段时验证失败,因为SubmittedData确实是一个数组。我一直在互联网上浏览并阅读symfony的文档,但似乎找不到找到与symfony 2.7相同的行为的方法。
我将不胜感激任何建议,我已经坚持了一段时间
答案 0 :(得分:0)
Symfony从v2.7更改为4.0,更改了许多默认值;
我遇到了同样的问题,经过2个小时的调查,
我最终添加了属性compound
和allow_extra_field
。
因此,这应该可以解决您的问题:
$builder->add('contactData', null, [
'mapped' => false,
'compound' => true,
'allow_extra_fields' => true,
])
编辑:
这没有按预期工作,最终我没有出现错误,也没有内容作为提交的数据,所以我创建了一个新类型来在预提交事件中动态添加字段,如下所示:
UnstructuredType.php
<?php
namespace ASTechSolutions\Bundle\DynamicFormBundle\Form\Type;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\FormBuilderInterface;
use Symfony\Component\Form\FormEvent;
use Symfony\Component\Form\FormEvents;
use Symfony\Component\Form\FormInterface;
/**
* Class UnstructuredType.
*
* This class is created to resolve the change of form's behaviour introduced in https://github.com/symfony/symfony/pull/29307
* From v3.4.21, v4.1.10 and v 4.2.2, Symfony requires defining fields and don't accept arrays on a TextType for ex.
* TODO: this is a temporary solution and needs refactoring by declaring explicitly what fields we define, and then accept on requests
*
*/
class UnstructuredType extends AbstractType
{
/**
* {@inheritDoc}
*/
public function buildForm(FormBuilderInterface $builder, array $options)
{
$builder->addEventListener(FormEvents::PRE_SUBMIT, function (FormEvent $event) {
$this->addChildren($event->getForm(), $event->getData());
});
}
/**
* @param FormInterface $form
* @param $data
*/
public function addChildren(FormInterface $form, $data)
{
if (is_array($data)) {
foreach ($data as $name => $value) {
if (!is_array($value)) {
$form->add($name);
} else {
$form->add($name, null, [
'compound' => true
]);
$this->addChildren($form->get($name), $value);
}
}
} else {
$form->add($data, null, [
'compound' => false,
]);
}
}
}
答案 1 :(得分:0)
在另一个答案中不需要@ sym183461的UnstructuredType。
该信息在其他字段中。
您定义类似@ sym183461的字段:
$builder->add('contactData', null, [
'mapped' => false,
'compound' => true,
'allow_extra_fields' => true,
])
然后您可以执行以下操作:
$contactData = $form->get('contactData')->getExtraFields()
您所有的数据都在其中,并且可以在深层结构中正常工作。