在更新另一个实体的同时创建一个实体 [英] Creating an entity while updating another

查看:32
本文介绍了在更新另一个实体的同时创建一个实体的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个问题似乎找不到答案.

I have one question I don't seem to find an answer to.

我的用户实体带有状态"字段.

I have my User entity with a "Status" field.

我想要做的是在每次更改用户状态时在另一个表StatusEvent"中存储一个新行,以跟踪用户状态的历史记录.

What I want to do is store in another table "StatusEvent" a new line each time the status of a user is changed to keep track of the history of statuses of my users.

我尝试使用 PreUpdate 方法,但它不允许在此步骤中创建新实体.

I tried to work with the PreUpdate method but it doesn't allow the creation of new Entities in this step.

我可能在想其他事件也可能(onFlush 也许?),但这些没有来自 PreUpdate 的 LifecycleEventArgs 的方法(它允许知道字段是否已更改).

I was maybe thinking that it might be possible with other events (onFlush maybe?) but these do not have the methods of the LifecycleEventArgs from PreUpdate (which allows to know if a field has been changed).

有人已经遇到过相同的模式或对我如何实现它有想法吗?

Anyone has already came across a same pattern or has an idea on how I could implement it?

提前致谢,

推荐答案

@Dimitris 的解决方案可行,但需要您手动调度事件.

The solution by @Dimitris would work, but requires you to dispatch the event manually.

我会使用您提到的 onFlush 方法.(如果你正在写一个库,你最好使用自定义事件)

I would use the onFlush method like you mentioned. (If you are writing a library, you are better off with the custom event)

您可以使用 UnitOfWork 来获取更改集.

You can use UnitOfWork to get the change sets.

public function onFlush(OnFlushEventArgs $event)
{
    $em = $event->getEntityManager();
    $uow = $em->getUnitOfWork();

    foreach ($uow->getScheduledEntityInsertions() as $entity) {
        $this->newEntities[] = $entity;

        if ($entity instanceof User) {
            $changeSet = $uow->getEntityChangeSet($entity);

            // if the $changeSet contains the status, log the change
            $log = new Log();

            $em->persist($log);
            $uow->computeChangeSet($em->getClassMetadata(Log::class), $log);
        }
    }

    foreach ($uow->getScheduledEntityUpdates() as $entity) {
        // same here, create a private method to avoid duplication
    }
}

这个监听器的权衡是它只会在刷新时记录事情.如果您的实体在刷新前多次更改状态,则只会记录最后一个状态.例如 state1 -> 2 -> 3 只会被记录为 state1 -> 3

The trade off of this listener is it will only log things on flush. If your entity changes state multiple times before flush, only the last state will be logged. Eg state1 -> 2 -> 3 will only be logged as state1 -> 3

如果您计划创建具有许多状态和转换的复杂状态字段,请查看工作流组件并使用那里的侦听器.这需要更多的工作,但非常值得.

If you plan on creating a complex status field with many states and transitions have a look at the workflow component and use the listeners from there. It is a bit more work, but well worth it.

这篇关于在更新另一个实体的同时创建一个实体的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆