Karrimor88
Karrimor88

Reputation: 3

cascade={"persist"} doesn't work when entity is updated (but it does at the creation)

I have two Entities with a relation ManyToOne between them.

My first entity look like this:

<?php
    [...] //namespace, use and stuff
/**
 * @ORM\Table()
 * @ORM\Entity(repositoryClass="Project\MyBundle\Entity\Entity1Repository")
 * @ORM\HasLifecycleCallbacks()
 */
class Entity1
{
    [...] //id and stuff
//
    /**
     * @ORM\OneToMany(targetEntity="Project\MyBundle\Entity\Entity2", mappedBy="entity1", cascade={"persist"})
     */
    private $entities2;
//
    public function __construct() {
        $this->entities2 = new ArrayColleciont();
        [...]
    }
    [...] // Getter Setter and stuff
//
    /**
     *@ORM\PreUpdate()
     *@ORM\PrePersist()
     */
    public function newEntity2() {
        $this->entities2->add(new Entity2($this));
    }

And my second look like that:

<?php
    [...]//namespace, use and stuff
/**
 * @ORM\Table()
 * @ORM\Entity(repositoryClass="Project\MyBundle\Entity\Entity2Repository")
 */
class Entity2
{
    [...]// id and stuff
//
    /**
     * @ORM\ManyToOne(targetEntity="Project\MyBundle\Entity\Entity1", inversedBy="Entities2")
     */
    private $entity1;
//
    public function __construct(Entity1 $entity1) {
        $this->entity1 = $entity1;
        [...]
    }

The point is. When I create a new Entity1 and I persist it, a Entity2 is created too and saved in database. BUT, when I simply update my Entity1 the method "newEntity2" is still called but nothing is saved in database.

My guess is, it come from the cascade="persist" option.

Upvotes: 0

Views: 912

Answers (2)

Andras
Andras

Reputation: 171

preUpdate is too late to change anything. The changes already calculated and doctrine know what sqls to run to save your changes. (it is effectively happens before running the sql update)

onFlush is a better option if you want to track changes (will be fired on creation of your entities also).

Just don't forget, that at this stage, if you change a property or create / delete an entity, you need to ask doctrine manually to re-check the changes you made. (read the lines under the code sample in doctrine docs: http://doctrine-orm.readthedocs.org/projects/doctrine-orm/en/latest/reference/events.html#onflush)

Upvotes: 0

Richard
Richard

Reputation: 4119

From the documentation on lifecycle events:

prePersist - The prePersist event occurs for a given entity before the respective EntityManager persist operation for that entity is executed. It should be noted that this event is only triggered on initial persist of an entity (i.e. it does not trigger on future updates).

So persist will only be useful on the first load.

From the documentation on preUpdate

Changes to associations of the updated entity are never allowed in this event

Changes to fields of the passed entities are not recognized by the flush operation

So preUpdate is not what you want.

I would look into implementing an event listener, probably onFlush, you can do whatever you please in this event.

Upvotes: 1

Related Questions