2013-01-04 30 views
31

OneToManyからCの関係を持つのエンティティABの関係を作成しました。ディープクローン関係するエンティティを持つDoctrineエンティティ

このAエンティティをクローンし、新しいIDでデータベースに設定する必要があります。また、すべての深い関係は新しいidsでクローン化されるべきです。

私は何をしようとしたことはnullA IDを設定することです:

$A = clone $A_original; 
$A->setId(null); 
$em->persist($A); 

それはAテーブルに新しいレコードを作成しますが、BCではありません。

Aエンティティの完全コピーを作成するにはどうすればよいですか?

答えて

47

idをnullに設定し、必要に応じて関係をクローンするエンティティに__clone()メソッドを実装する必要があります。関連するオブジェクトにidを保持すると、新しいエンティティAが既存のエンティティBCとの関係を持つとみなされるためです。

Aためのクローン方法:

public function __clone() { 
    if ($this->id) { 
     $this->setId(null); 
     $this->B = clone $this->B; 
     $this->C = clone $this->C; 
    } 
} 

BCのためのクローン方法:

coder4のコメントに基づいて
public function __clone() { 
    if ($this->id) { 
     $this->setId(null); 
    } 
} 

https://groups.google.com/forum/?fromgroups=#!topic/doctrine-user/Nu2rayrDkgQ

https://doctrine-orm.readthedocs.org/en/latest/cookbook/implementing-wakeup-or-clone.html

DeepCopyと呼ば

public function __clone() { 
    if ($this->id) { 
     $this->setId(null); 

     // cloning the relation M which is a OneToMany 
     $mClone = new ArrayCollection(); 
     foreach ($this->M as $item) { 
      $itemClone = clone $item; 
      $itemClone->setA($this); 
      $mClone->add($itemClone); 
     } 
     $this->M = $mClone; 
    } 
} 
+0

中関係のクローンを作成するより簡単な方法を設立し、それはしていないようですOneToMany、何かのアイデアに取り組む理由は? – coder4show

+1

@ coder4showこれは、あなたが 'ArrayCollection'を複製し、その中の要素ではないためです。 OneToMany関係のクローンメソッドを追加しました。 – flec

+0

この例では、OneToMany関係は正しくクローンされません。これは、クローンされた関連エンティティが引き続き古いエンティティを参照するためです。動作例については、[この回答](http://stackoverflow.com/a/28313673/3215645)を参照してください。 – Richard

6

これを行いますモジュールもあります::$this->MはOneToManyので、ArrayCollectionあるA上OneToMany関係のためのクローン方法を示す

https://github.com/myclabs/DeepCopy

$deepCopy = new DeepCopy(); 
$myCopy = $deepCopy->copy($myObject); 

フィルタを追加して、コピープロセスをカスタマイズすることもできます。

+0

こんにちは@ベンあなたは[this]を見てみることができます(http://stackoverflow.com/questions/28650001/clone-entity-in-cascade-mode?noredirect=1#comment45641837_28650001) – ReynierPM

+1

私はこの信じられないほどバグが見つかりました独自の 'clone'メソッドをロールバックする方が速い –

0

私はDeepCloneを(それがPHPを必要と7.1以降)を使用することができ波平、私はこれの唯一の問題は、あるエンティティ__clone方法

$this->tags = new ArrayCollection($this->tags->toArray()); 
関連する問題