pim-community-dev icon indicating copy to clipboard operation
pim-community-dev copied to clipboard

PreSave event is not PreSave

Open gernhard1337 opened this issue 2 years ago • 2 comments

:bug: The akeneo.storage.pre_save is not triggerd before saving :bug:

In Akeneo 5.0 a Event listener on the event akeneo.storage.pre_save has as its argument an event with the subject of type ProductInterface. Since this event should get triggerd before a save, the product shall be different if retrieved by a productQueryBuilder in the eventListener. However, if i listen to this event and compare the products, one from the event, the other one retrieved by a pqb, they are the same which shall not occur.

Expected behaviour would be that the product from the event shall be different to the product from pqb. The product from pqb shall be the product before the update and product from event should have the new values

gernhard1337 avatar Jan 21 '23 18:01 gernhard1337

or did i missunderstand the concept? i want to have a listener which gets the difference in a product update. My thoughts were that i listen to a preSave event and retrieve the non saved product for a comparison

gernhard1337 avatar Jan 21 '23 18:01 gernhard1337

Hey, I've ran into the same problem a couple of days ago and I thought that sharing my situation could help you and others that might find this topic..

This is where the akeneo.storage.pre_save is being dispatched, so be sure that you don't overwrite that file and if you do, be sure that you still dispatch that symfony event.

I believe that this is not a bug, but please take everything I say with a grain of salt.. PreSave event is called when an entity is already updated, but not yet in the database. So if you query for an entity - you will get... Lets say "Committed" entity, but it was not already "Pushed" to the database, BUT it was already updated, so the entity that you would take from... Lets say repository, would be the same as the entity that you get from GenericEvent class.

Above explanation has to do something with doctrine, but im relatively new to it so once more, please take it with a grain of salt..

I've found some solutions to this problem:

  1. Use doctrine PreUpdate listener, that should get you a changeset of the updated entity. More on doctrine PreUpdate event, which is being called from doctrine UnitOfWork.
  2. Make your own symofny preUpdate event, which would pass original entity and the updated data. You would probably want to dispatch this event right about here.
  3. Get UnitOfWork class trough EntityManager class, from UnitOfWork you can get original entity data as an array. I would say that this is not as good as first and second solution, but that could work..
  4. Query your database directly for the updated entity(This is probably the ugliest and one of the worst ways to go around this situation and it should be avoided).

Similar topic that I found while looking for this.

Username070 avatar Apr 02 '23 19:04 Username070