mirror of
https://github.com/doctrine/orm.git
synced 2026-03-23 22:42:18 +01:00
DDC-1680: Id is null in postRemove events #2110
Reference in New Issue
Block a user
Delete Branch "%!s()"
Deleting a branch is permanent. Although the deleted branch may continue to exist for a short time before it actually gets removed, it CANNOT be undone in most cases. Continue?
Originally created by @doctrinebot on GitHub (Mar 5, 2012).
Originally assigned to: @beberlei on GitHub.
Jira issue originally created by user redemption:
When using the postRemove event, $this->id (where id is the annotated @Id of the Entity) is null.
All other fields have the correct data (eg if you have an Entity with name, email, address, and id as fields, the id field is the only one that is null).
@doctrinebot commented on GitHub (Mar 5, 2012):
Comment created by @beberlei:
This is expected behavior, otherwise when you merge that entity back it will be detected as "known", although its actually deleted. You can save the id in preRemove and then reuse it in postRemove if you need it.
@doctrinebot commented on GitHub (Mar 5, 2012):
Issue was closed with resolution "Invalid"
@doctrinebot commented on GitHub (Mar 5, 2012):
Comment created by redemption:
Is there any chance of providing a native premade value (or method) to store the deleted id, for instance "deletedId"? It seems logical to me that postRemove events will need to know the Id that was removed, and hacking it in with preRemove events all the time is less elegant.
@doctrinebot commented on GitHub (Sep 17, 2014):
Comment created by umed:
yeah I also think that we need something native. This hack with preremove looks really ugly.
@doctrinebot commented on GitHub (Sep 17, 2014):
Comment created by umed:
Here is https://groups.google.com/forum/#!topic/doctrine-user/bTukzq0QrSE a very good comment left by Pavel Horal
@doctrinebot commented on GitHub (Sep 17, 2014):
Comment created by @ocramius:
[~umed] I'm fine with reverting this, but it needs a new and well exposed issue.
@doctrinebot commented on GitHub (Jan 12, 2015):
Comment created by ahmadnazir:
There there another issue created for this problem? If not, then I would like to help.
What do you mean by a well exposed issue?
@doctrinebot commented on GitHub (Jan 12, 2015):
Comment created by @ocramius:
[~ahmadnazir] I mean that we could need a functional test case
@doctrinebot commented on GitHub (Oct 20, 2015):
Comment created by pawelbaranski:
Hi,
I'd also see this issue solved. I have a case where I'm storing an entity both in MySQL and part of it in Elasticsearch. When I delete an entity from MySQL I'd like it to be deleted from ES as well. I would not want to remove it from ES too soon so postRemove event would be what I need.
I will use the hack Benjamin presented, but it is like an unwanted child
@ebuildy commented on GitHub (Nov 4, 2017):
Why this is closed?
@lcobucci commented on GitHub (Nov 21, 2017):
@ebuildy apparently nobody bothered to create a "new and well exposed issue" (which means it has a clear explanation and a functional test) as @Ocramius asked. Would you be wiling to do that?
You can find examples of functional tests on
388afb46d0/tests/Doctrine/Tests/ORM/Functional/Ticket@dkarlovi commented on GitHub (Jan 18, 2018):
@lcobucci if I'm creating a test case, it's a PR against master or where?
@lcobucci commented on GitHub (Jan 18, 2018):
@dkarlovi you can use
2.6as base.@dkarlovi commented on GitHub (Jan 26, 2018):
Until I create the test, it get's reviewed, accepted/rejected/fixed/released, I need the described workaround.
Where exactly am I supposed to store the identifier in the preRemove handler? On the event? But it's not the same object in preRemove and postRemove. I imagine we can abuse PHP's synchronous nature and store as a property inside my handler and count on things not getting out of order, but that's just too messy for comfort, TBH.
IMO if this state is the solution for
then this exact problem needed a better solution. For example, mark the entity as "deleted" or "unmergeable" or something.
@Ocramius commented on GitHub (Jan 26, 2018):
I usually record everything I need to "keep" in
onFlush, which right after the changes in theUnitOfWorkwere computed.The id being
nullis currently by design, so we'd break BC for a scenario like this if we reverted it:@dkarlovi commented on GitHub (Jan 26, 2018):
@Ocramius thanks, makes sense.
I know, that was my point with
so, when you try to merge it back, it just throws. This allows for correct behavior in both cases (entity which is deleted is a orphaned entity you still have a reference to, you still don't get to reuse it just like that).
@Ocramius commented on GitHub (Jan 26, 2018):
->merge()will no longer be improved, and is deprecated (and removed in3.x@dkarlovi commented on GitHub (Jan 26, 2018):
Sorry, "merge" is a lapsus, I meant "when you try to treat it as a regular entity in any way" (persist, update, etc).
@Ocramius commented on GitHub (Jan 26, 2018):
Ah, sorry. No, there is no way to do that. After
flush(), memory usage must stay constant in the ORM, and adding a registry that marks removed entities would be a big issue.@dkarlovi commented on GitHub (Jan 26, 2018):
Fair point.
Would a better workaround be to introduce a new event type,
PostRemoveEventArgswhich would havegetIdentifier()? Then Doctrine can do this for you and I wouldn't be too bad.@Ocramius commented on GitHub (Jan 26, 2018):
@dkarlovi we can improve this in 3.x by adding the identifier to
PostRemoveEventArgsor by breaking BC as I described in https://github.com/doctrine/doctrine2/issues/2326#issuecomment-360719911@ismail1432 commented on GitHub (Jan 23, 2019):
One year later, I think it's a good idea 👍
@Nathanael-Shermett commented on GitHub (Jan 5, 2021):
Another two years later, and I also think it's a good idea.
It doesn't make sense to modify an entity class (or perhaps every entity class), complete with getters and setters, just to store a historical ID. It's hacky, and it subverts the entity's integrity. With that said, I have a hacky solution that is at least self-contained:
I'm sure some purists on here will say this is gross. I agree. However, this limitation shouldn't exist in the first place, and a man's gotta eat somehow.
@Warxcell commented on GitHub (May 10, 2021):
I suggest just to move
https://github.com/doctrine/orm/blob/2.8.x/lib/Doctrine/ORM/UnitOfWork.php#L1244-L1246
after
https://github.com/doctrine/orm/blob/2.8.x/lib/Doctrine/ORM/UnitOfWork.php#L1248-L1250.
That will bring the ID in
postRemoveevents. I think it's not convenient to havegetIdentifierin event, for examples on places like that: https://github.com/Warxcell/files/blob/master/src/NamingStrategy/IdToPathStrategy.php+1 for BC-break, It would be nice to have the ID even after
postRemove. The use case is, when/if https://github.com/doctrine/dbal/pull/4622 is accepted, I will be able to refactor my listener onpostRemoveit will collect entities for removal, and ononTransactionCommitI can loop over pending entities for removal and call$fileManager->remove($entity)which could useIDto determine the path to the file. That will be impossible if IDs are gone after postRemove.@Nathanael-Shermett commented on GitHub (Nov 15, 2021):
FYI, my above fix (using a dynamic property to store the entity ID before it is lost during the delete process) will be deprecated in PHP 8.2 and will throw an error in PHP 9.0.
You can read more here.
@justin-oh commented on GitHub (May 16, 2024):
For anyone searching in the future, I had to do something like the following to maintain an ID-based value (which was a directory path).
Before:
After:
@orangevinz commented on GitHub (May 28, 2024):
Using a trait can be convenient as well
@Richardds commented on GitHub (Jun 2, 2024):
@orangevinz Unfortunately, the trait methods won't get registered as Lifecycle callbacks.