2016-07-28 1 views
1

Je travaille sur un projet où je suis obligé d'utiliser cascade = { « supprimer », « persistent »} à cause de la problem described here.Comment supprimer une utilisation de cascade = {"remove", "persist"} des entités de Symfony2?

lecture à travers le documentation, pour citer:

Même si La cascade automatique est pratique, elle doit être utilisée avec précaution. N'appliquez pas aveuglément cascade = all à toutes les associations car cela dégradera inutilement les performances de votre application. Pour chaque opération en cascade qui est activée, Doctrine applique également cette opération à l'association, qu'elle soit unique ou valorisée.

Et je vois que la même chose peut être fixé si j'utilise

$em->persist($entity); 

Dans mes services de persistance, que je suis déjà appel. Cependant, la doctrine ne fonctionne pas comme prévu. Voici mes entités.

Entité/Employee.php

<?php 
namespace AppBundle\Entity; 

use Doctrine\ORM\Mapping AS ORM; 

/** 
* @ORM\Entity 
* @ORM\Table(uniqueConstraints={@ORM\UniqueConstraint(
*    name="UNIQ_EMPLOYEE_ID_NAME_ADDRESS_STATE_CITY_COUNTRY", 
*    columns={"id","name","city","state","country"} 
*  )}) 
*/ 
class Employee 
{ 
    /** 
    * @ORM\Id 
    * @ORM\Column(type="integer", options={"unsigned":true}) 
    * @ORM\GeneratedValue(strategy="NONE") 
    */ 
    private $id; 

    /** 
    * @ORM\Column(type="string", length=255, nullable=false) 
    */ 
    private $name; 

    /** 
    * @ORM\Column(type="text", nullable=false) 
    */ 
    private $address; 

    /** 
    * @ORM\Column(type="string", length=255, nullable=false) 
    */ 
    private $city; 

    /** 
    * @ORM\Column(type="string", length=255, nullable=false) 
    */ 
    private $state; 

    /** 
    * @ORM\Column(type="string", length=255, nullable=false) 
    */ 
    private $country; 


    /** 
    * @ORM\ManyToOne(targetEntity="AppBundle\Entity\Department", inversedBy="employee", cascade={"remove","persist"}) 
    * @ORM\JoinColumn(name="department_id", referencedColumnName="id", nullable=false) 
    */ 
    private $department; 

    /** 
    * @ORM\OneToMany(targetEntity="AppBundle\Entity\Transfer", mappedBy="employee", cascade={"remove","persist"}) 
    */ 
    private $transfer; 
} 

?> 

Entité/Department.php

<?php 
namespace AppBundle\Entity; 

use Doctrine\ORM\Mapping AS ORM; 
use Doctrine\Common\Collections\ArrayCollection; 
use Doctrine\Common\Collections\Collection; 
use Doctrine\Common\Collections\Selectable; 

/** 
* @ORM\Entity 
* @ORM\Table(uniqueConstraints={@ORM\UniqueConstraint(
*    name="UNIQ_DEPARTMENT_ID_NAME", 
*    columns={"id","name"} 
*  )}) 
*/ 
class Department 
{ 
    /** 
    * @ORM\Id 
    * @ORM\Column(type="integer", options={"unsigned":true}) 
    * @ORM\GeneratedValue(strategy="NONE") 
    */ 
    private $id; 

    /** 
    * @ORM\Column(type="string", length=255, nullable=false) 
    */ 
    private $name; 

    /** 
    * @ORM\OneToMany(targetEntity="AppBundle\Entity\Employee", mappedBy="department", cascade={"remove","persist"}) 
    */ 
    private $employee; 

    /** 
    * @ORM\OneToMany(targetEntity="AppBundle\Entity\Transfer", mappedBy="department", cascade={"remove","persist"}) 
    */ 
    private $transfer; 
} 

?> 

Entité/Transfer.php

<?php 
namespace AppBundle\Entity; 

use Doctrine\ORM\Mapping AS ORM; 
use Doctrine\Common\Collections\ArrayCollection; 
use Doctrine\Common\Collections\Collection; 
use Doctrine\Common\Collections\Selectable; 

/** 
* @ORM\Entity 
* @ORM\Table(uniqueConstraints={@ORM\UniqueConstraint(
*    name="UNIQ_TRANSFER_ID_DEPARTMENT_EMPLOYEE_START_END", 
*    columns={"id","name"} 
*  )}) 
*/ 
class Transfer 
{ 
    /** 
    * @ORM\Id 
    * @ORM\Column(type="integer", options={"unsigned":true}) 
    * @ORM\GeneratedValue(strategy="AUTO") 
    */ 
    private $id; 

    /** 
    * @ORM\Column(type="date", length=255, nullable=false) 
    */ 
    private $start; 

    /** 
    * @ORM\Column(type="date", length=255, nullable=false) 
    */ 
    private $end; 

    /** 
    * @ORM\ManyToOne(targetEntity="AppBundle\Entity\Employee", inversedBy="attendance", cascade={"persist","remove"}) 
    * @ORM\JoinColumn(name="employee_id", referencedColumnName="id", nullable=false) 
    */ 
    private $employee; 

    /** 
    * @ORM\ManyToOne(targetEntity="AppBundle\Entity\Department", inversedBy="attendance", cascade={"persist","remove"}) 
    * @ORM\JoinColumn(name="department_id", referencedColumnName="id", nullable=false) 
    */ 
    private $department; 
} 

?> 

MISE À JOUR 1:

Maintenant, j'ai un autre problème. Étant donné que ma stratégie GeneratorValue pour l'employé et le département sont AUCUN, j'ai un problème avec l'erreur d'enregistrement en double. J'essaie d'utiliser PreFlushEventArgs pour supprimer l'entité avant de persister si l'enregistrement existe dans la base de données. Mais je me demande si cela devrait être aussi complexe?

Merci pour votre aide à l'avance.

Répondre

2

Il semble que vous ayez une opération de cascade persistante de l'employé vers le département et le transfert. Mais ils mettent en cascade l'opération de persistance à l'entité des employés aussi.

Cela signifie que lorsque vous faites

$em->persist($an_employee); 

Vous êtes coincé dans une boucle persistent. À mon avis, la cascade persistante ne devrait être que d'une seule façon, c'est-à-dire uniquement sur l'entité Employee.

Aussi, si vous choisissez de faire, ajoutez votre service à l'employé, et non le contraire:

$an_employee->addDepartment($a_department); 
$an_employee->addTransfer($a_transfer); 

De cette façon, lorsque vous persistez un employé, ses départements et le transfert devrait être persista trop

+0

J'ai mis à jour ma question, voir .. si vous pouvez m'aider. Je pense que je devrais mettre à jour via le modèle de transfert car un employé pourrait être préexistant. – Gaurav