Php 通过外国实体在同花顺上的例外实现同一身份的原则
我有Php 通过外国实体在同花顺上的例外实现同一身份的原则,php,symfony,doctrine-orm,doctrine,Php,Symfony,Doctrine Orm,Doctrine,我有User和UserProfileOneToOne-相关实体。它们应该始终成对存在,没有UserProfile就不应该有User 用户应该从autoincrement获取其id,而UserProfile应该具有用户id。因此,它们都应该具有相同的id,并且没有其他列来设置关系() UserProfile的id同时是主键(PK)和外键(FK) 我设法设置了它,但它要求先保存用户,然后在单独的步骤中创建并保存UserProfile 我想要的是,UserProfile总是在构造函数中使用User创建
User
和UserProfile
OneToOne-相关实体。它们应该始终成对存在,没有UserProfile
就不应该有User
用户应该从autoincrement获取其id,而UserProfile应该具有用户id。因此,它们都应该具有相同的id,并且没有其他列来设置关系()
UserProfile的id同时是主键(PK)和外键(FK)
我设法设置了它,但它要求先保存用户,然后在单独的步骤中创建并保存UserProfile
我想要的是,UserProfile总是在构造函数中使用User创建的,但是如果我这样做,我会得到以下异常:
条令\ORM\ORMInvalidArgumentException:类型为'AppBundle\entity\UserProfile'(AppBundle\entity)的给定实体\UserProfile@0000000052e1b1eb00000000409c6f2c)未设置标识/标识值。无法将其添加到身份映射。
请参阅下面的代码–它可以工作,但不是我想要的方式。php注释显示了我想要实现的目标
Test.php
:
/**
* It works, both saving and loading.
* BUT, it requires that I create and save UserProfile
* in a separate step than saving User step.
*/
// create and save User
$user = new User();
$objectManager->persist($user);
$objectManager->flush();
// create and save UserProfile (this should be unnecessary)
$user->createProfile()
$objectManager->flush();
use Doctrine\ORM\Mapping as ORM;
/**
* @ORM\Entity(repositoryClass="AppBundle\Entity\UserRepository")
* @ORM\Table(name="users")
*/
class User
{
/**
* @var int
*
* @ORM\Column(name="uid", type="integer")
* @ORM\Id
* @ORM\GeneratedValue(strategy="AUTO")
*/
private $id;
/**
* It's NULL at first, I create it later (after saving User).
*
* @var UserProfile|null
*
* @ORM\OneToOne(targetEntity="UserProfile", mappedBy="user", cascade="persist")
*/
private $profile = null;
public function __construct()
{
// I want to create UserProfile inside User's constructor,
// so that it is always present (never NULL):
//$this->profile = new UserProfile($this);
// but this would give me error:
//
// Doctrine\ORM\ORMInvalidArgumentException:
// The given entity of type 'AppBundle\Entity\UserProfile'
// (AppBundle\Entity\UserProfile@0000000058af220a0000000079dc875a)
// has no identity/no id values set. It cannot be added to the identity map.
}
public function createProfile()
{
$this->profile = new UserProfile($this);
}
}
use Doctrine\ORM\Mapping as ORM;
/**
* @ORM\Entity
* @ORM\Table(name="profiles")
*/
class UserProfile
{
/**
* – UserProfile's "uid" column points to User's "uid" column
* – it is PK (primary key)
* - it is FK (foreign key) as well
* – "owning side"
*
* @var User
*
* @ORM\Id
* @ORM\OneToOne(targetEntity="User", inversedBy="profile")
* @ORM\JoinColumn(name="uid", referencedColumnName="uid", nullable=false)
*/
private $user;
public function __construct(User $user)
{
$this->user = $user;
}
}
User.php
:
/**
* It works, both saving and loading.
* BUT, it requires that I create and save UserProfile
* in a separate step than saving User step.
*/
// create and save User
$user = new User();
$objectManager->persist($user);
$objectManager->flush();
// create and save UserProfile (this should be unnecessary)
$user->createProfile()
$objectManager->flush();
use Doctrine\ORM\Mapping as ORM;
/**
* @ORM\Entity(repositoryClass="AppBundle\Entity\UserRepository")
* @ORM\Table(name="users")
*/
class User
{
/**
* @var int
*
* @ORM\Column(name="uid", type="integer")
* @ORM\Id
* @ORM\GeneratedValue(strategy="AUTO")
*/
private $id;
/**
* It's NULL at first, I create it later (after saving User).
*
* @var UserProfile|null
*
* @ORM\OneToOne(targetEntity="UserProfile", mappedBy="user", cascade="persist")
*/
private $profile = null;
public function __construct()
{
// I want to create UserProfile inside User's constructor,
// so that it is always present (never NULL):
//$this->profile = new UserProfile($this);
// but this would give me error:
//
// Doctrine\ORM\ORMInvalidArgumentException:
// The given entity of type 'AppBundle\Entity\UserProfile'
// (AppBundle\Entity\UserProfile@0000000058af220a0000000079dc875a)
// has no identity/no id values set. It cannot be added to the identity map.
}
public function createProfile()
{
$this->profile = new UserProfile($this);
}
}
use Doctrine\ORM\Mapping as ORM;
/**
* @ORM\Entity
* @ORM\Table(name="profiles")
*/
class UserProfile
{
/**
* – UserProfile's "uid" column points to User's "uid" column
* – it is PK (primary key)
* - it is FK (foreign key) as well
* – "owning side"
*
* @var User
*
* @ORM\Id
* @ORM\OneToOne(targetEntity="User", inversedBy="profile")
* @ORM\JoinColumn(name="uid", referencedColumnName="uid", nullable=false)
*/
private $user;
public function __construct(User $user)
{
$this->user = $user;
}
}
UserProfile.php
:
/**
* It works, both saving and loading.
* BUT, it requires that I create and save UserProfile
* in a separate step than saving User step.
*/
// create and save User
$user = new User();
$objectManager->persist($user);
$objectManager->flush();
// create and save UserProfile (this should be unnecessary)
$user->createProfile()
$objectManager->flush();
use Doctrine\ORM\Mapping as ORM;
/**
* @ORM\Entity(repositoryClass="AppBundle\Entity\UserRepository")
* @ORM\Table(name="users")
*/
class User
{
/**
* @var int
*
* @ORM\Column(name="uid", type="integer")
* @ORM\Id
* @ORM\GeneratedValue(strategy="AUTO")
*/
private $id;
/**
* It's NULL at first, I create it later (after saving User).
*
* @var UserProfile|null
*
* @ORM\OneToOne(targetEntity="UserProfile", mappedBy="user", cascade="persist")
*/
private $profile = null;
public function __construct()
{
// I want to create UserProfile inside User's constructor,
// so that it is always present (never NULL):
//$this->profile = new UserProfile($this);
// but this would give me error:
//
// Doctrine\ORM\ORMInvalidArgumentException:
// The given entity of type 'AppBundle\Entity\UserProfile'
// (AppBundle\Entity\UserProfile@0000000058af220a0000000079dc875a)
// has no identity/no id values set. It cannot be added to the identity map.
}
public function createProfile()
{
$this->profile = new UserProfile($this);
}
}
use Doctrine\ORM\Mapping as ORM;
/**
* @ORM\Entity
* @ORM\Table(name="profiles")
*/
class UserProfile
{
/**
* – UserProfile's "uid" column points to User's "uid" column
* – it is PK (primary key)
* - it is FK (foreign key) as well
* – "owning side"
*
* @var User
*
* @ORM\Id
* @ORM\OneToOne(targetEntity="User", inversedBy="profile")
* @ORM\JoinColumn(name="uid", referencedColumnName="uid", nullable=false)
*/
private $user;
public function __construct(User $user)
{
$this->user = $user;
}
}
测试应用程序:请记住,实际对象需要由EntityManager保存。 仅仅将该类作为对另一个类的引用并不会使entityManager意识到这两个类都存在的事实 您应该将实际的userProfile持久化到EntityManager,以便能够保存关系 因负面评论而更新: 请阅读条令文件。。。你应该坚持 以下示例是本章用户评论示例的扩展。假设在我们的应用程序中,每当用户写第一条评论时,就会创建一个用户。在这种情况下,我们将使用以下代码:
<?php
$user = new User();
$myFirstComment = new Comment();
$user->addComment($myFirstComment);
$em->persist($user);
$em->persist($myFirstComment);
$em->flush();
您应该考虑创建包含EntyMealMead的UService服务,并负责创建、链接和持久化用户+用户配置文件实体。
ID是数据库的事情,而不应该是模型中的一个问题。不要认为它们需要相同的主键值。或者如果做不到这一点,就放弃一个需要自动,另一个不需要的概念。@Cerad我正在一个遗留应用程序上构建——数据库就是它。我需要将原则调整到当前模式,而不是相反…另外,上面的代码可以工作。条令可以处理作为主键的外键。它只是不能在一次刷新中持久化实体。或者至少我在寻找答案,如何配置条令,这样就可以了。足够公平了。如果你做一个搜索,那么你会发现这个问题的几百种变体。所有答案都相同。请参阅,您似乎需要更改关系的拥有方。不,由于cascade=“persist”
,配置文件已匹配以保持。如果我删除它并“手动”保留配置文件,问题仍然存在。这没有帮助,我已经尝试过了(现在,为了完全确定,我甚至再试一次)。同样的错误。/app/console-cache:clear&&sudo/etc/init.d/nginx-restart&&sudo/etc/init.d/php5-fpm-restart&&sudo/etc/init.d/memcached-restart&/app/console-cache:clear
你能分享一下你是如何尝试单独持久化的吗?见报告:测试在这里: