zfcuser 学说实体与 bjyauthorize 的 ManyToOne 关联

ManyToOne association for zfcuser doctrine entity with bjyauthorize

我在我的 zf2 项目中使用 zfcuser doctrine 模块和 bjyauthorize,它工作得很好。现在我想从我的用户实体中获取连接的国家/地区实体

在User.php中:

/**
 * An example of how to implement a role aware user entity.
 *
 * @ORM\Entity
 * @ORM\Table(name="users", indexes={
 *      @ORM\Index(name="fk_User_Country1_idx", columns={"Country_id"}), 
 * }, uniqueConstraints={@ORM\UniqueConstraint(name="email_UNIQUE", columns={"email"})})
 * @ORM\HasLifecycleCallbacks()
 */
class User implements UserInterface, ProviderInterface
{

...

/**
 * @var ersEntity\Country
 * @ORM\ManyToOne(targetEntity="Country", inversedBy="users")
 * @ORM\JoinColumn(name="Country_id", referencedColumnName="id")
 */
protected $country;

在Country.php

/**
 * Entity\Country
 *
 * @ORM\Entity()
 * @ORM\Table(name="Country")
 * @ORM\HasLifecycleCallbacks()
 */
class Country implements InputFilterAwareInterface
{

...

/**
 * @ORM\OneToMany(targetEntity="User", mappedBy="country")
 * @ORM\JoinColumn(name="id", referencedColumnName="Country_id")
 */
protected $users;

我的一个控制器中的简单 testAction 失败:

$user = $em->getRepository("ersEntity\Entity\User")
    ->findOneBy(array('id' => 1));
error_log($user->getFirstname().' '.$user->getSurname());
error_log('country: '.$user->getCountry()->getName());

这导致:

[Tue May 19 00:02:44 2015] [error] [client 185.17.207.16] Andi N.
[Tue May 19 00:02:44 2015] [error] [client 185.17.207.16] PHP Fatal error:  Call to a member function getName() on a non-object in /home/ers/www/ers/module/Admin/src/Admin/Controller/TestController.php on line 172

我想知道为什么无法从用户实体中获取国家/地区实体。对于同一个项目中的其他实体,这工作正常。

有人能告诉我需要做什么才能从这个 zfcuser-bjyauthorize-doctrine 用户实体中获取国家实体吗?

有关更多代码信息,整个项目可在 https://github.com/inbaz/ers 开发分支中找到。

编辑:

对于没有设置国家/地区的用户,需要出现错误。确实需要检查一个国家是否存在。但是这个用户有一个国家集。我通过 phpmyadmin 检查过。无法通过 getCountry() 方法获取此国家/地区实体。

也许这是导致将学说实体反序列化和序列化到会话中的原因。我检查了 doctrine documentation 如何将实体保存到会话中。但我想将所有子实体保留在会话中,所以在我的例子中,我在会话中有一个订单实体,它包含多个包实体。每个包实体都有一个用户和多个项目实体。当从会话中取回订单实体时,我希望能够访问所有这些元素。

我什至尝试对会话中的每个用户进行合并,例如:

foreach($participants as $participant) {
    $participant = $em->merge($participant);
}

但这并没有改变任何东西。即使对整个订单进行合并也不成功。

您是否知道如何从具有完整学说特征的会话中获取学说实体?

我觉得一切都很好。起初我以为您的实体定义中缺少您的 getCountry 方法,但我看到了 it is there

我猜 ID 为 1 的用户没有设置国家/地区。转到您的 table(phpmyadmin 或其他)并检查 Country_id 列的值。 如果您希望每个用户都有一个国家/地区,您可以根据 the Doctrine2 @JoinColumn specs 通过将 nullable=false 添加到您的连接列定义来确保您的数据完整性。

否则(如果 $country 允许 null)你应该在拉 getName() 之前先检查国家是否是一个对象:

$countryName = null;
$country = $user->getCountry();
if(is_object($country)){
    $countryName = $country->getName();
}
/** @var null|string $countryName */
$countryName  //... use your country name which is null or string

还有一件事,我强烈建议 table 仅使用 小写 字符串列 个名字。使用大写可能会给您带来麻烦。

编辑

我仔细看了看,现在你的映射是错误的。你use doctrine to validate your schema了吗?在关系的反面(Country.php 里面)有一个 @ORM\JoinColumn。反面不需要这个 @ORM\JoinColumn 声明。你应该删除这一行。拥有方是用户,因此连接列定义应该只在那里声明。

应该是这样的:

Country.php:

/**
 * @var Collection
 * @ORM\OneToMany(targetEntity="User", mappedBy="country")
 */
protected $users;

User.php:

/**
 * @var Country
 * @ORM\ManyToOne(targetEntity="Country", inversedBy="users")
 * @ORM\JoinColumn(name="Country_id", referencedColumnName="id")
 */
protected $country;

Doctrine 2: Can entities be saved into sessions?

这就是我的问题的答案。

if a lazy-loaded entity is not loaded at serialization time, it won't be loadable after de-serialization. So you have to make sure the entity is fully loaded before serializing it.

如果无法创建新的条令实体并获取反序列化实体的数组副本并将此数据填充到新实体中,则问题仍然悬而未决。