27

Within the same entity I have a PreUpdate and a PrePersist. The PreUpdate fires, but the PrePersist never does. I put a die() after the flush and comments within the lifecycle callbacks. Full entity can be seen at http://pastebin.com/yUk1u4GQ

Entity callbacks

/**
* @PreUpdate
*/
public function fixDates(){
    $this->updatedOn = $this->getNow();
    $this->closedDate = null;
    $this->openDate = null;
    print "dates fixed";
}

/**
* @PrePersist
*/
public function prePersist() {
    print 'in prePersist';
    die();
}

Entity Manager calls

$em->persist($school);

$em->flush();
die();

My screen reads "dates fixed", but not the prePersist message. I do have the @HasLifecycleCallbacks at the top of the entity.

j0k
  • 22,600
  • 28
  • 79
  • 90
Tom
  • 1,971
  • 3
  • 22
  • 32

5 Answers5

67

Don't forget to enable Lifecycle Callbacks in your class annotation :

/**
 * Report\MainBundle\Entity\Serveur
 * @ORM\HasLifecycleCallbacks
 */
class Serveur {
Thierry Daguin
  • 865
  • 7
  • 11
41

PrePersist is fired only when you are performing INSERT statement, not UPDATE statement.

When testing, don't forget that the UPDATE statement is fired only when the entity attributes really change. If the Entity Manager is being called to persist that entity, it first looks if there are any changes. If not, no sql query is performed and no @PreUpdate method is called.

j0k
  • 22,600
  • 28
  • 79
  • 90
Johan
  • 843
  • 8
  • 10
  • 1
    Upvoted. I found this out the hard way too (via step debugging) when my code was not working as I expected. IMO the current documentation does not make this clear enough, for what is an easy mistake to make. – iainp999 May 30 '14 at 12:33
11

I know this question is almost 2 years old, but I just had the exact same problem and since this doesn't have an accepted answer I want to share one last thing everyone else forgot to mention.

Although it seems that the triggered method will be used only by the entity class itself, it's scope should be kept public. My method wasn't triggering just because I marked it as a protected one. I hope this will help someone.

Martini
  • 166
  • 1
  • 7
6

I just had the same problem. Hope this helps you:

I forgot to import the annotations with the use statement. If you try this dont forget to add the "ORM" prefix:

use Doctrine\ORM\Mapping as ORM;

// ...

/**
* @ORM\PreUpdate
*/
public function preUpdate()
{
}
Besnik
  • 6,469
  • 1
  • 31
  • 33
5

Maybe it version dependent but my working annotations have a next view:

Life cycle class annotation:

/**
 * @Entity @Table(name="table_name")
 * @HasLifecycleCallbacks
 **/

Events annotations:

/** @PrePersist **/
/** @PreUpdate **/

That is all that i have in Model.

Urgotto
  • 863
  • 7
  • 6
  • Yes!! According to docs in doctrine 2 Marks a method on the entity to be called as a @ PrePersist event. Only works with @ HasLifecycleCallbacks in the entity class PHP DocBlock. – Leonardo Beal Aug 16 '17 at 06:43