我有一个用户实体。那些用户可以在一起成为朋友。所以我定义了一个自我引用manyToMany单向关联(因为总是互惠是友谊,对吗?)。
YML中的一个用户实体
manyToMany:
friendList:
targetEntity: User
joinTable:
name: user_friend
joinColumns:
user_id:
referencedColumnName: id
inverseJoinColumns:
friend_id:
referencedColumnName: id
cascade: [persist]
当我致电$user->addFriendList($friend)
时,在坚持和同花顺之后,我有PDOException
:
SQLSTATE [23000]:完整性约束违规:1062重复条目“1-2”为fey'PRIMARY'
当我签入日志时,我可以看到该学说正在尝试两次执行相同的插入查询。
为了您的信息,我的addFriendList
功能
public function addFriendList(User $friend)
{
if (!$this->friendList->contains($friend)) {
$this->friendList[] = $friend;
$friend->addFriendList($this);
}
}
我在哪里错了?
答案 0 :(得分:5)
我终于找到了解决问题的方法。但是,我仍然不知道它是否是Doctrine2缺陷,或者它是否按设计工作。
我需要在添加好友之前坚持我的用户并刷新。
所以我的工作代码是:
$em->persist($user);
$em-flush();
$user->addFriendList($friend);
$em->persist($user);
$em->flush();
答案 1 :(得分:2)
@Reuven,你写道:
$this->friendList[] = $friend;
$friend->addFriendList($this);
好吧,你要两次插入关系。
这应该足够了:
$this->friendList[] = $friend;
答案 2 :(得分:1)
这是因为你没有指定mappedBy(拥有方)和反转方。
查看用户和角色之间的这种多对多关系:
/**
* @ORM\Entity
* @ORM\Table(name="user")
*/
class User
{
/**
* @ORM\ManyToMany(targetEntity="Role", mappedBy="users")
* @ORM\JoinTable(name="user_role",
* joinColumns={@ORM\JoinColumn(name="user_id", referencedColumnName="id")},
* inverseJoinColumns={@ORM\JoinColumn(name="role_id", referencedColumnName="id")}
* )
*/
protected $roles;
/**
* Constructor
*/
public function __construct()
{
$this->roles = new ArrayCollection();
}
/**
* Has role
*
* @param Role $role
* @return bool
*/
public function hasRole(Role $role)
{
return $this->roles->contains($role);
}
/**
* Add role
*
* @param Role $role
*/
public function addRole(Role $role)
{
if (!$this->hasRole($role)) {
$this->roles->add($role);
$role->addUser($this);
}
}
/**
* Remove roles
*
* @param Role $role
*/
public function removeRole(Role $role)
{
if ($this->hasRole($role)) {
$this->roles->removeElement($role);
$role->removeUser($this);
}
}
}
/**
* @ORM\Entity
* @ORM\Table(name="role")
*/
class Role implements RoleInterface
{
/**
* @ORM\ManyToMany(targetEntity="User", inversedBy="roles")
* @ORM\JoinTable(name="user_role",
* joinColumns={@ORM\JoinColumn(name="role_id", referencedColumnName="id")},
* inverseJoinColumns={@ORM\JoinColumn(name="user_id", referencedColumnName="id")}
* )
*/
private $users;
public function __construct()
{
$this->users = new ArrayCollection();
}
/**
* Has user
*
* @param User $user
* @return bool
*/
public function hasUser(User $user)
{
return $this->users->contains($user);
}
/**
* Add user
*
* @param User $user
*/
public function addUser(User $user)
{
if (!$this->hasUser($user)) {
$this->users->add($user);
$user->addRole($this);
}
}
/**
* Remove user
*
* @param User $user
*/
public function removeUser(User $user)
{
if ($this->hasUser($user)) {
$this->users->removeElement($user);
$user->addRole($this);
}
}
/**
* Get users
*
* @return ArrayCollection
*/
public function getUsers()
{
return $this->users;
}