2017-05-26 62 views
0

我有以下SZENARIO:实体的用户时,另一实体的用户中创建的实体不叫

  • 用户创建一个Scan
  • ScanSubscriberprePersistpreUpdateonFlush
  • onFlush一些可能会发生的罕见情况需要CampaignParticipation(与给定的Scan有关)才能完成。我在这里更新了一些其他实体,并且我还为相关用户创建了一个AccountBalanceChange。之后我只需拨打$unitOfWork->computeChangeSets();

直到这一点,这个工作很好。现在的问题:

  • 我还有另一个AccountBalanceChangeSubscriberpostPersist。所以我期望当我坚持在我的ScanSubscriber中创建的AccountBalanceChange时调用此订阅者,但这不会发生。

我也尝试过的东西,如:

$cmf = $entityManager->getMetadataFactory(); 
$meta = $cmf->getMetadataFor(get_class($accountBalanceChange)); 
$unitOfWork->computeChangeSet($meta, $accountBalanceChange); 

所以我的问题是:

  • 是我的期望正确的,这个监听器应该被称为还是有有点在“堆积听众”限制?
  • 还是我错过了一些“注册”,使框架知道新的实体,无论在数据库中是否保持正确?

AccountBalanceChangeSubscriber本身就像一个魅力,当我使用奏鸣曲管理员保存AccountBalanceChange

我的代码(很短):

ScanSubscriber.php

class ScanSubscriber implements EventSubscriber 
{ 
    public function getSubscribedEvents() 
    { 
     return array(
      'onFlush', 
     ); 
    } 

    public function onFlush(OnFlushEventArgs $args) 
    { 
     $entityManager = $args->getEntityManager(); 
     $unitOfWork = $entityManager->getUnitOfWork(); 

     foreach ($unitOfWork->getScheduledEntityUpdates() as $entity) { 
      if ($entity instanceof Scan) { 
       $accountBalanceChange = new AccountBalanceChange(); 

       $entityManager->persist($accountBalanceChange); 
      } 
     } 

     $unitOfWork->computeChangeSets(); 
    } 
} 

AccountBalanceChangeSubscriber.php

class AccountBalanceChangeSubscriber implements EventSubscriber 
{ 
    public function getSubscribedEvents() 
    { 
     return array(
      'postPersist', 
     ); 
    } 

    public function postPersist(LifecycleEventArgs $args) 
    { 
     // This is never called in the case I described but works when I save the entity using sonata admin 
    } 
} 
+1

我只是在分析你的代码的时候查看https://github.com/Atlantic18/DoctrineExtensions/blob/v2.4.x/lib/Gedmo/Loggable/LoggableListener.php。由于操作非常相似。你有没有试过显式调用'$ unitOfWork-> computeChangeSet($ entityManager-> getClassMetadata($ accountBalanceChange),$ accountBalanceChange)'后保留? – Flosculus

+1

不确定这是否是问题,但postPersist只有在实际INSERT发生后才能运行([here's](https://github.com/doctrine/doctrine2/blob/2a239be45ec4e64c736e4277cde8bff376ef2402/lib/Doctrine/ORM/UnitOfWork.php#L1024-L1026) )'UnitOfWork :: executeInserts'中的相关代码) – malarzm

+1

对于原则监听器有一个巨大的限制,特别是当试图更改实体时。基本上,您正在尝试在持久层操作期间执行业务逻辑。可能想看看你是否可以完全在Doctrine之外实现所需的功能。 – Cerad

回答

0

最后我决定重构我的代码的逻辑,从 “二” 听者移动分成一个独立的命令。就在我完成这个任务时,我想出了一个非常复杂的“特征”链,这使得我认为用户没有被调用。其实它被调用,一切工作如我所料,我的问题还有另一个UserSubscriber是不允许的被标记为anonymousUser差不多所有的财产的变化(在我的情况,直到他们“要求”他们的帐户) 。我忘记将我想更改的两个房产列入白名单AccountBalanceChange

所以,感谢评论,指导我以正确的方式,并有一个愉快的周末! :-)

相关问题