0

私のアプリケーションでは、私は8スロットのシガーヒュミドールエンティティを持っています。私は各スロットに何百本もの葉巻を入れたいと思っています。葉巻を1つのヒュミドールに1回追加することはできますが、別の葉巻に交換して同じ葉巻を追加することはできませんスロット1に接続します。私はそれが問題ではないと確信していましたが、別のヒュミドールにいることで問題はないと思っていましたが、今例外を取得しています。"An exception occurred while executing 'UPDATE humidor SET slot_1 = ? WHERE id = ?' with params [2, 8]:SQLSTATE[23000]: Integrity constraint violation: 1062 Duplicate entry '2' for key 'UNIQ_4AE64E7F3CF622F8'"'私は教義の専門家ではなく、モデリングについてどうすればよいかについて完全にはわかりません。どんなアドバイスも素晴らしいだろう。あなたは1対1のマッピングを持っているとして、ここsymfonyリレーショナルマッピングが1対多

は教義がそれらの列に一意のインデックスを作成し、スロット

/** 
* Humidor 
* 
* @ORM\Table(name="humidor") 
* @ORM\Entity(repositoryClass="AppBundle\Repository\HumidorRepository") 
*/ 

class Humidor 
{ 
    /** 
    * @var int 
    * 
    * @ORM\Column(name="id", type="integer") 
    * @ORM\Id 
    * @ORM\GeneratedValue(strategy="AUTO") 
    */ 
    private $id; 

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

/** 
* @ORM\ManyToOne(targetEntity="UserBundle\Entity\User", inversedBy="humidors") 
* @ORM\JoinColumn(name="user_id", referencedColumnName="id") 
*/ 
private $user; 

/** 
* @ORM\OneToOne(targetEntity="Cigar") 
* @ORM\JoinColumn(name="slot_1", referencedColumnName="id") 
*/ 
private $slot1; 

/** 
* @ORM\OneToOne(targetEntity="Cigar") 
* @ORM\JoinColumn(name="slot_2", referencedColumnName="id") 
*/ 
private $slot2; 

    /** 
    * @ORM\OneToOne(targetEntity="Cigar") 
    * @ORM\JoinColumn(name="slot_3", referencedColumnName="id") 
    */ 
private $slot3; 

    /** 
    * @ORM\OneToOne(targetEntity="Cigar") 
    * @ORM\JoinColumn(name="slot_4", referencedColumnName="id") 
    */ 
private $slot4; 

    /** 
    * @ORM\OneToOne(targetEntity="Cigar") 
    * @ORM\JoinColumn(name="slot_5", referencedColumnName="id") 
    */ 
private $slot5; 

    /** 
    * @ORM\OneToOne(targetEntity="Cigar") 
    * @ORM\JoinColumn(name="slot_6", referencedColumnName="id") 
    */ 
private $slot6; 

    /** 
    * @ORM\OneToOne(targetEntity="Cigar") 
    * @ORM\JoinColumn(name="slot_7", referencedColumnName="id") 
    */ 
private $slot7; 

    /** 
    * @ORM\OneToOne(targetEntity="Cigar") 
    * @ORM\JoinColumn(name="slot_8", referencedColumnName="id") 
    */ 
private $slot8; 

、その後、私のシガーエンティティ

/** 
* Cigar 
* 
* @ORM\Table(name="cigar") 
* @ORM\Entity(repositoryClass="AppBundle\Repository\CigarRepository") 
* @ORM\HasLifecycleCallbacks() 
*/ 
class Cigar 
{ 
    /** 
    * @ORM\PrePersist() 
    */ 
    public function onPrePersist(){ 
     $this->setName($this->getManufacturer()->getName() . " " . $this->getVariant()); 
} 

/** 
* @var int 
* 
* @ORM\Column(name="id", type="integer") 
* @ORM\Id 
* @ORM\GeneratedValue(strategy="AUTO") 
*/ 
private $id; 

/** 
* @var int 
* 
* @ORM\Column(name="gauge", type="integer") 
*/ 
private $gauge; 

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

/** 
* @var string 
* 
* @ORM\Column(name="wrapper_country", type="string", length=255) 
*/ 
private $wrapperCountry; 

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

/** 
* @var string 
* 
* @ORM\Column(name="description", type="text") 
*/ 
private $description; 

/** 
* @var string 
* 
* @ORM\Column(name="filler_country", type="string", length=255) 
*/ 
private $fillerCountry; 

/** 
* @ORM\ManyToOne(targetEntity="Manufacturer", inversedBy="cigars") 
* @JoinColumn(name="manufacturer_id", referencedColumnName="id") 
*/ 
private $manufacturer; 

/** 
* @ORM\ManyToOne(targetEntity="Wrapper", inversedBy="cigars") 
* @JoinColumn(name="wrapper_id", referencedColumnName="id") 
*/ 
private $wrapper; 

/** 
* @ORM\ManyToOne(targetEntity="Shape", inversedBy="cigars") 
* @JoinColumn(name="shape_id", referencedColumnName="id") 
*/ 
private $shape; 

/** 
* @ORM\Column(type="string") 
* 
*/ 
private $image; 

/** 
* @var string 
* @ORM\Column(type="string") 
*/ 
private $name; 

答えて

0

とヒュミドールです。のは、この例を考えてみましょう(それがこの例で十分だと私は単一のスロットのみを残してきた):

id slot_1 
1  11 
2  12 

これは、あなたがそれぞれ12をヒュミドールするために割り当てられたIDが1112と2葉巻を有することを意味します。 slot_1コラムにユニークなインデックスがあります。これにより、1つのシガーが2つの異なるヒュミドールに属さないことが保証されます。

あなたがそれらを切り替えるしようとすると、次のSQL文が生成されます。

残念ながら
UPDATE humidors SET slot_1 = 12 WHERE id = 1; 
UPDATE humidors SET slot_1 = 11 WHERE id = 2; 

データベースは葉巻12が一度ヒュミドール12の両方にすることはできませんので、最初の文は、実行できません。

最も簡単な解決策は、1対1の関係を多対1(1つの$slotXフィールド)に変更することです。これにより一意の制約が削除されます。そうでなければ、逆の関係がないため、 。さらに、8つのスロットがあり、葉巻がこれらのいくつかに属していないので(私が正しく理解していれば)、ルールはデータベース自体によって厳密に制御されていません。

別の方法は、一時的なNULL値などでそれらを切り替えることですが、2つの別々のフラッシュ文が必要になり、オプションでデータベース内の矛盾した状態を避けるためにこれらをトランザクションで手動で折り返す必要があるので、doctrineではさらに難しくなります。