使用Symfony2验证嵌入表单

时间:2015-12-06 21:13:31

标签: php forms validation symfony

我有一个Parents表单嵌入到另一个表单Student中,其中包含学生家长的数据。我需要验证嵌入的表单,因为在我的代码中只是对另一个表单进行验证。

StudentType.php

  //...
  ->add('responsible1', new ParentsType(),array('label' => 'Mother'))
  ->add('responsible2', new ParentsType(),array('label'=> 'Father'))

 /**
 * @param OptionsResolverInterface $resolver
 */
public function setDefaultOptions(OptionsResolverInterface $resolver)
{
    $resolver->setDefaults(array(
        'data_class' => 'BackendBundle\Entity\Student'
    ));
}

实体父母

 //...
 /**
 * @ORM\OneToMany(targetEntity="Student", mappedBy="$responsible1")
 * @ORM\OneToMany(targetEntity="Student", mappedBy="$responsible2")
 */
 private $students;

实体学生

 //...
 /**
 * 
 * @ORM\ManyToOne(targetEntity="Parents", inversedBy="students", cascade={"persist"})
 */
 private $responsible1;

/**
 * 
 * @ORM\ManyToOne(targetEntity="Parents", inversedBy="students", cascade={"persist"})
 */
 private $responsible2;

在控制器中使用以下代码,我得到了主窗体(Student)中所有无效字段的名称和错误消息,但是我得到了嵌入式窗体(父母)的错误,只是得到名称对象(responsible1或responsible2)和我得到的消息[object Object]。

StudentController.php

protected function getErrorMessages(\Symfony\Component\Form\Form $form) 
{
    $errors = array();

    foreach ($form->getErrors() as $key => $error) {
        $errors[] = $error->getMessage();
    }

    foreach ($form->all() as $child) {
        if (!$child->isValid()) {
            $errors[$child->getName()] = $this->getErrorMessages($child);
        }
    }

    return $errors;
}
/**
 * Creates a new Student entity.
 *
 */
public function createAction(Request $request)
{
// if request is XmlHttpRequest (AJAX) but not a POSt, throw an exception
if ($request->isXmlHttpRequest() && !$request->isMethod('POST')) {
    throw new HttpException('XMLHttpRequests/AJAX calls must be POSTed');
}

    $entity = new Student();
    $form = $this->createCreateForm($entity);
    $form->handleRequest($request);

    if ($form->isValid()) {

        $em = $this->getDoctrine()->getManager();
        $em->persist($entity);
        $em->flush();

        if ($request->isXmlHttpRequest()) {
        return new JsonResponse(array('message' => 'Success!'), 200);
    }

        return $this->redirect($this->generateUrl('student_show', array('id' => $entity->getId())));
    }

     if ($request->isMethod('POST')) {
                    return new JsonResponse(array(
        'result' => 0,
        'message' => 'Invalid form',
        'data' => $this->getErrorMessages($form)),400);
    }

    return $this->render('BackendBundle:Student:new.html.twig', array(
        'entity' => $entity,
        'form'   => $form->createView(),
    ));
}

我尝试使用函数getErrorsAsString()的上述代码来处理字符串中的错误,所以如果它们全部出现,那么我想我必须在上面的代码中添加一些内容以便在&#时验证对象34; responsible1"或者"负责2"验证所有字段。

我需要让所有这些错误都是两个表单上的无效字段。我读了一些代码添加'cascade_validation' => truevalidation_group@Assert\Valid()的内容,但我尝试了但我没有得到它。如果有人能向我解释一些值得的东西,我感谢你,因为我对这一切都不熟悉。

1 个答案:

答案 0 :(得分:2)

以下示例flatterns表单和子表单错误到assoc数组中,让我知道这是否是你想要实现的目标

<?php
namespace Example\Bundle\UtilityBundle\Form;
use Symfony\Component\Form\Form;
class FormErrors
{
    public function getArray(Form $form, $style = 'KO')
    {
        $method = sprintf('get%sErrors', $style);

        $messages = $this->$method($form->all());

        return $messages;
    }

    private function getKOErrors(Form $children)
    {
        $errors = array();

        /* @var $child \Symfony\Component\Form\Form */
        foreach ($children as $child) {
            $type = $child->getConfig()->getType()->getName();
            if ($child->count()  && ($type !== 'choice')) {
                $childErrors = $this->getKOErrors($child->all());
                if (sizeof($childErrors)) {
                    $errors = array_merge($errors, $childErrors);
                }
            } else {
                if (!$child->isValid()) {
                    // I need only one error message per field 
                    $errors[$child->getName()] = $child->getErrors()->current()->getMessage();
                }
            }
        }

        return $errors;
    }
}