Symfony2:在实体 class 中获取 security.context
Symfony2 : get security.context inside entity class
是否可以在实体 class 中获取 security.context
?
我知道以下内容不起作用。我不知道如何实现 $user
部分。
/**
* Set createdAt
*
* @ORM\PrePersist
*/
public function setCreatedAt()
{
$user = $this->get('security.context')->getToken()->getUser();
$this->owner = $user->getId();
$this->createdAt = new \DateTime();
$this->updatedAt = new \DateTime();
}
确实这是错误的。
保持简单,您想在创建实体时设置实体的所有者吗?将它传递给您的实体构造函数并将其设置在那里。
旁注 我建议使用 prePersist 和 preUpdate 生命周期回调来处理实体时间戳。这个库 (php 5.4+) 提供了一组非常简单的工具来实现这些功能:https://github.com/KnpLabs/DoctrineBehaviors
对于日期时间:
对于时间戳,您最好使用@hasLifeCycleCallback 注释和一些标记为@prePersist 和@preUpdate 的附加方法。
对于创建,您甚至可以在 __constructor 本身中进行。
请注意,您必须对 $updatedAt 属性 使用 @preUpdate,@prePersist 仅适用于新实体。
如果您有很多实体需要这个,您可以考虑使用 Doctrine2 侦听器来防止重复代码。
所有权属性:
如果您总是想将实体的所有权设置为 "currently logged in user",您最好使用 Doctrine2 侦听器或订阅者。
这样你就不必将这个逻辑添加到你的控制器,或者任何你需要创建实体的地方。
http://symfony.com/doc/current/cookbook/doctrine/event_listeners_subscribers.html
http://docs.doctrine-project.org/projects/doctrine-orm/en/latest/reference/events.html#onflush
按照文档创建侦听器服务,确保它使用构造函数获取安全上下文。
将它设置为 onFlush 事件,这样您就可以在实际保存之前调整实体。这是处理这种事情最好的活动。
确保遵循 Doctrine 文档 onFlush 章节中的脚注,否则 Doctrine 不会接受最后一分钟的更改。
您的听众应该看起来像:
class FlushExampleListener
{
public function onFlush(OnFlushEventArgs $eventArgs)
{
$em = $eventArgs->getEntityManager();
$uow = $em->getUnitOfWork();
foreach ($uow->getScheduledEntityInsertions() as $entity) {
if ($entity instanceof YourClass) {
// change owner
$entity->setOwner($this->securityContext->getToken()->getUser());
// tell doctrine you changed it
$uow->recomputeSingleEntityChangeSet($em->getClassMetadata(get_class($entity)), $entity);
}
}
foreach ($uow->getScheduledEntityUpdates() as $entity) {
if ($entity instanceof YourClass) {
// change owner
$entity->setOwner($this->securityContext->getToken()->getUser());
// tell doctrine you changed it
$uow->recomputeSingleEntityChangeSet($em->getClassMetadata(get_class($entity)), $entity);
}
}
}
}
请注意,这不会检查用户是否实际登录...
是否可以在实体 class 中获取 security.context
?
我知道以下内容不起作用。我不知道如何实现 $user
部分。
/**
* Set createdAt
*
* @ORM\PrePersist
*/
public function setCreatedAt()
{
$user = $this->get('security.context')->getToken()->getUser();
$this->owner = $user->getId();
$this->createdAt = new \DateTime();
$this->updatedAt = new \DateTime();
}
确实这是错误的。
保持简单,您想在创建实体时设置实体的所有者吗?将它传递给您的实体构造函数并将其设置在那里。
旁注 我建议使用 prePersist 和 preUpdate 生命周期回调来处理实体时间戳。这个库 (php 5.4+) 提供了一组非常简单的工具来实现这些功能:https://github.com/KnpLabs/DoctrineBehaviors
对于日期时间:
对于时间戳,您最好使用@hasLifeCycleCallback 注释和一些标记为@prePersist 和@preUpdate 的附加方法。 对于创建,您甚至可以在 __constructor 本身中进行。
请注意,您必须对 $updatedAt 属性 使用 @preUpdate,@prePersist 仅适用于新实体。
如果您有很多实体需要这个,您可以考虑使用 Doctrine2 侦听器来防止重复代码。
所有权属性:
如果您总是想将实体的所有权设置为 "currently logged in user",您最好使用 Doctrine2 侦听器或订阅者。 这样你就不必将这个逻辑添加到你的控制器,或者任何你需要创建实体的地方。
http://symfony.com/doc/current/cookbook/doctrine/event_listeners_subscribers.html http://docs.doctrine-project.org/projects/doctrine-orm/en/latest/reference/events.html#onflush
按照文档创建侦听器服务,确保它使用构造函数获取安全上下文。 将它设置为 onFlush 事件,这样您就可以在实际保存之前调整实体。这是处理这种事情最好的活动。
确保遵循 Doctrine 文档 onFlush 章节中的脚注,否则 Doctrine 不会接受最后一分钟的更改。
您的听众应该看起来像:
class FlushExampleListener
{
public function onFlush(OnFlushEventArgs $eventArgs)
{
$em = $eventArgs->getEntityManager();
$uow = $em->getUnitOfWork();
foreach ($uow->getScheduledEntityInsertions() as $entity) {
if ($entity instanceof YourClass) {
// change owner
$entity->setOwner($this->securityContext->getToken()->getUser());
// tell doctrine you changed it
$uow->recomputeSingleEntityChangeSet($em->getClassMetadata(get_class($entity)), $entity);
}
}
foreach ($uow->getScheduledEntityUpdates() as $entity) {
if ($entity instanceof YourClass) {
// change owner
$entity->setOwner($this->securityContext->getToken()->getUser());
// tell doctrine you changed it
$uow->recomputeSingleEntityChangeSet($em->getClassMetadata(get_class($entity)), $entity);
}
}
}
}
请注意,这不会检查用户是否实际登录...