Symfony2:以多对一的形式防止数据库中的重复 [英] Symfony2: Prevent duplicate in database with form Many to One

查看:22
本文介绍了Symfony2:以多对一的形式防止数据库中的重复的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我将一个家长表单嵌入到另一个表单 Student 中,其中包含一个学生的家长的数据,并且具有多对一的关联.

I have a Parents form embedded into another form Student containing the data of the parents of a student with an association of Many to one.

当一个新学生注册时,他的父母被记录在数据库的另一个表中.那么如果新同学是现有的兄弟需要注册,也就是说父母已经在数据库中注册了,应该防止父母再次在数据库中注册,只能升级了.

When a new student registration are recorded his parents in another table in the database. Then if a new student who is brother of an existing need to register, meaning that parents are already registered in the database, should be prevented from parents to register again in the database, could only upgrade .

我听说这是使用数据转换器解决的,但我不知道如何使用它.如果有人可以帮助我,我将不胜感激.这里我留下代码:

I'm told that this is solved using data transformers, but I do not know how to use it. If someone could help me I would appreciate it. Here I leave the code:

StudentType.php

StudentType.php

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

实体父母

     /**
 * @var integer
 *
 * @ORMColumn(name="id", type="integer")
 * @ORMId
 * @ORMGeneratedValue(strategy="AUTO")
 */
private $id;

//National identity document
//we have removed "@UniqueEntity(fields={"NID"}, message="...")" 
//so you can put any NID on the form and then check its existence to insert or not.
/**
 * @var string
 *
 * @ORMColumn(name="NID", type="string", length=10)
 * @AssertNotBlank()
 */
private $nid;

 //more properties...

 /**
 * @ORMOneToMany(targetEntity="Student", mappedBy="$responsible1")
 * @ORMOneToMany(targetEntity="Student", mappedBy="$responsible2")
 */
 private $students;

 //...
 public function addStudent(ColeBackendBundleEntityStudent $students)
{
    $this->students[] = $students;

    return $this;
}

public function removeStudent(ColeBackendBundleEntityStudent $students)
{
    $this->students->removeElement($students);
}

public function getStudents()
{
    return $this->students;
}

实体学生

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

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

 //...

public function setResponsible1($responsible1)
{
    $this->responsible1 = $responsible1;

    return $this;
}


public function getResponsible1()
{
    return $this->responsible1;
}


public function setResponsible2($responsible2)
{
    $this->responsible2 = $responsible2;

    return $this;
}

public function getResponsible2()
{
    return $this->responsible2;
}

ParentsRepository.php

ParentsRepository.php

 class ParentsRepository extends EntityRepository
 {
   public function findResponsible($nid)
   {
    return $this->getEntityManager()->createQuery(
        'SELECT p FROM BackendBundle:Parents p WHERE p.nid=:nid')
    ->setParameter('nid',$nid)
    ->setMaxResults(1)
    ->getOneOrNullResult();
   }
 }

StudentController.php

StudentController.php

/**
 * Creates a new Student entity.
 *
 */
public function createAction(Request $request)
{
    $entity = new Student();
    $form = $this->createCreateForm($entity);
    $form->handleRequest($request);

    if ($form->isValid()) {

    $responsible1 = $em->getRepository('BackendBundle:Parents')->findResponsible($entity->getResponsible1()->getNid());
    $responsible2 = $em->getRepository('BackendBundle:Parents')->findResponsible($entity->getResponsible2()->getNid());

   if($responsible1){
         $entity->setResponsible1($responsible1->getId()); 
   }
   if($responsible2){
         $entity->setResponsible2($responsible2->getId()); 
   }
   $entity->getResponsible1()->setUsername($entity->getResponsible1()->getNid());
   $entity->getResponsible2()->setUsername($entity->getResponsible2()->getNid());

   $entity->getResponsible1()->setPassword($entity->getResponsible1()->getNid());
   $entity->getResponsible2()->setPassword($entity->getResponsible2()->getNid());


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


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

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

用上面的代码试图解决问题但是它给我错误将数据持久化到数据库并且不会让我添加到数据库中,但是如果您使用以下代码来测试新学生创建并分配相应的父母不要再次创建它们(假设您之前已经创建过).

With the above code attempts to solve the problem but it gives me error to persist data to the database and will not let me add to the database, but if you use the following code to test the new student creates and assigns parents corresponding not create them again (assuming you were already created earlier).

    $responsible1 = $em->getRepository('BackendBundle:Parents')->findResponsible(4); //The number corresponds to the id of the parent
    $responsible2 = $em->getRepository('BackendBundle:Parents')->findResponsible(5);

    $entity->setResponsible1($responsible1->getId()); 
    $entity->setResponsible2($responsible2->getId()); 

我不知道我的做法是否正确.我读过一些将数据转换器或事件侦听器用作 PrePersist 和 Preupdate 的内容,但我不知道如何使用它.

I do not know if what I'm doing is right.I read something to use Data Transformers or event listener as PrePersist and Preupdate, but I don't know how to use this.

预先感谢您的回答.

推荐答案

代替

if($responsible1){
     $entity->setResponsible1($responsible1->getId()); 
}
if($responsible2){
     $entity->setResponsible2($responsible2->getId()); 
}
$entity->getResponsible1()->setUsername($entity->getResponsible1()->getNid());
$entity->getResponsible2()->setUsername($entity->getResponsible2()->getNid());

$entity->getResponsible1()->setPassword($entity->getResponsible1()->getNid());
$entity->getResponsible2()->setPassword($entity->getResponsible2()->getNid());

你可以写

if($responsible1){
     $entity->setResponsible1($responsible1); 
}
if($responsible2){
     $entity->setResponsible2($responsible2); 
}

它应该可以工作.

但我认为更好的解决方案是为 FormEvents::SUBMIT 事件添加一个事件监听器.此事件允许您从表单数据的规范化表示中更改数据.所以你需要做的就是这样:

But I think a better solution will be to add an event listener to the FormEvents::SUBMIT event. This event allows you to change data from the normalized representation of the form data. So all you need to do is something like this:

public function onSubmit(FormEvent $event)
{
   $student = $event->getData();

   if ($student->getResponsible1()) {
        $parentNid = $student->getResponsible1()->getNid();

        // here you check the database to see if you have a parent with this nid
        // if a parent exists, replace the current submitted parent data with the parent entity existing in your db
   }

希望这会有所帮助.如果我必须提供更多详细信息,请告诉我.

Hope this helps. Let me know if I have to give more details.

这篇关于Symfony2:以多对一的形式防止数据库中的重复的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆