我想要两个表 Person
和 Address
来共享它们的主键:
CREATE TABLE Person (id INT UNSIGNED NOT NULL AUTO_INCREMENT PRIMARY KEY);
CREATE TABLE Address (personId INT UNSIGNED NOT NULL PRIMARY KEY);
我试图模拟这样一种想法,即当您创建
Person
时,您也在为其创建 Address
。我想出了以下映射:
class Person
{
/**
* @Id
* @Column(type="integer")
* @GeneratedValue
*/
private $id;
/**
* @OneToOne(targetEntity="Address", cascade={"all"})
* @JoinColumn(name="id", referencedColumnName="personId")
*/
private $address;
public function __construct() {
$this->address = new Address($this);
}
}
class Address
{
/**
* @Id
* @OneToOne(targetEntity="Person")
* @JoinColumn(name="personId", referencedColumnName="id")
*/
private $person;
public function __construct(Person $person) {
$this->person = $person;
}
}
当我尝试坚持
Person
时,我希望它级联到 Address
,但我得到以下异常:Doctrine\ORM\ORMException
我不能明确地调用
flush()
,因为我没有明确地 persist()
ing Address
,而是我期望 Person
级联持久化 Address
。因此,据我所知,在适当的时候让
flush()
获得 id
应该是 Doctrine 的工作。当对
auto_increment
和 Person
使用不同的 Address
id 时,这种一对一的关系会很好地级联(但是我必须向 addressId
添加一个 Person
)。我的目标是让他们共享相同的
id
。那可能吗?
最佳答案
在学说 2.1 中使用 Identity through foreign Entities 怎么样?
在您的场景中,您可以使用 @ManyToOne
而不是 @OneToOne
关联。
编辑
当您保留拥有方时,关联将保留。在您的映射中,这是 Address
。更改您的映射,以便所有者拥有外键,并且一切正常。
/**
* @OneToOne(targetEntity="Address", cascade={"all"}, inversedBy="person")
* @JoinColumn(name="id", referencedColumnName="personId")
*/
private $address;
换句话说,如果 Address
应该是 Person
的所有者,那么您必须首先将 Address
持久化以保持关联。如果您希望关联与
Person
持久化,那么您应该将 Person
标记为拥有方,将 Address
标记为 的逆 方:/**
* @Id
* @OneToOne(targetEntity="Person", inversedBy="address")
* @JoinColumn(name="personId", referencedColumnName="id")
*/
private $person;
关于php - 共享主键的两个表上的一对一关系,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/19708898/