Skip to content

Commit

Permalink
Fix #4252 Cascade first before refreshing the entity itself so toMany…
Browse files Browse the repository at this point in the history
… associations are not reset to empty collections
  • Loading branch information
Zacharias Luiten authored and zluiten committed Apr 24, 2022
1 parent 676a1bb commit 17bc1ad
Show file tree
Hide file tree
Showing 2 changed files with 44 additions and 28 deletions.
4 changes: 2 additions & 2 deletions lib/Doctrine/ORM/UnitOfWork.php
Original file line number Diff line number Diff line change
Expand Up @@ -2216,12 +2216,12 @@ private function doRefresh($entity, array &$visited): void
throw ORMInvalidArgumentException::entityNotManaged($entity);
}

$this->cascadeRefresh($entity, $visited);

$this->getEntityPersister($class->name)->refresh(
array_combine($class->getIdentifierFieldNames(), $this->entityIdentifiers[$oid]),
$entity
);

$this->cascadeRefresh($entity, $visited);
}

/**
Expand Down
68 changes: 42 additions & 26 deletions tests/Doctrine/Tests/ORM/Functional/Ticket/GH4252Test.php
Original file line number Diff line number Diff line change
@@ -1,48 +1,60 @@
<?php

declare(strict_types=1);

namespace Doctrine\Tests\ORM\Functional\Ticket;

use Doctrine\Common\Collections\ArrayCollection;
use Doctrine\Common\Collections\Collection;
use Doctrine\ORM\Mapping\Column;
use Doctrine\ORM\Mapping\Entity;
use Doctrine\ORM\Mapping\GeneratedValue;
use Doctrine\ORM\Mapping\Id;
use Doctrine\ORM\Mapping\ManyToMany;
use Doctrine\ORM\Mapping\ManyToOne;
use Doctrine\ORM\Mapping\OneToMany;
use Doctrine\Tests\OrmFunctionalTestCase;

use function assert;

/**
* @group GH-4252
*/
class GH4252Test extends \Doctrine\Tests\OrmFunctionalTestCase
class GH4252Test extends OrmFunctionalTestCase
{
protected function setUp()
protected function setUp(): void
{
parent::setUp();

$this->_schemaTool->createSchema(array(
$this->_schemaTool->createSchema([
$this->_em->getClassMetadata(GH4252City::class),
$this->_em->getClassMetadata(GH4252Resident::class),
$this->_em->getClassMetadata(GH4252Address::class),
));
]);
}

public function testIssue()
public function testIssue(): void
{
$city = new GH4252City([new GH4252Resident([new GH4252Address()])]);

$this->_em->persist($city);
$this->_em->flush();
$this->_em->clear();

/** @var GH4252City $city */
$city = $this->_em->find(GH4252City::class, $city->getId());
assert($city instanceof GH4252City);
$city->setFlag(false);
/** @var GH4252Resident $resident */
$resident = $city->getResidents()->first();
assert($resident instanceof GH4252Resident);
$resident->setFlag(false);
/** @var GH4252Address $address */
$address = $resident->getAddresses()->first();
assert($address instanceof GH4252Address);
$address->setFlag(false);

$this->_em->refresh($city);

$resident = $city->getResidents()->first();
$address = $resident->getAddresses()->first();
$address = $resident->getAddresses()->first();

$this->assertTrue($city->getFlag());
$this->assertTrue($resident->getFlag());
Expand All @@ -57,7 +69,9 @@ class GH4252City
{
/**
* @var int
* @Id @Column(type="integer") @GeneratedValue
* @Id
* @Column(type="integer")
* @GeneratedValue
*/
private $id;

Expand All @@ -69,7 +83,6 @@ class GH4252City

/**
* @var GH4252Resident[]|Collection
*
* @OneToMany(targetEntity="Doctrine\Tests\ORM\Functional\Ticket\GH4252Resident", mappedBy="city", cascade={"persist","refresh"})
*/
private $residents;
Expand All @@ -81,25 +94,26 @@ public function __construct(array $residents)
$this->residents->add($resident);
$resident->setCity($this);
}

$this->flag = true;
}

public function getId() : int
public function getId(): int
{
return $this->id;
}

public function getFlag() : bool
public function getFlag(): bool
{
return $this->flag;
}

public function setFlag(bool $flag) : void
public function setFlag(bool $flag): void
{
$this->flag = $flag;
}

public function getResidents() : Collection
public function getResidents(): Collection
{
return $this->residents;
}
Expand Down Expand Up @@ -130,7 +144,6 @@ class GH4252Resident

/**
* @var GH4252Address[]|Collection
*
* @ManyToMany(targetEntity="Doctrine\Tests\ORM\Functional\Ticket\GH4252Address", fetch="EXTRA_LAZY", cascade={"persist","refresh"})
*/
private $addresses;
Expand All @@ -141,35 +154,36 @@ public function __construct(array $addresses)
foreach ($addresses as $address) {
$this->addresses->add($address);
}

$this->flag = true;
}

public function getId() : int
public function getId(): int
{
return $this->id;
}

public function getCity() : GH4252City
public function getCity(): GH4252City
{
return $this->city;
}

public function setCity(GH4252City $city) : void
public function setCity(GH4252City $city): void
{
$this->city = $city;
}

public function getFlag() : bool
public function getFlag(): bool
{
return $this->flag;
}

public function setFlag(bool $flag) : void
public function setFlag(bool $flag): void
{
$this->flag = $flag;
}

public function getAddresses() : Collection
public function getAddresses(): Collection
{
return $this->addresses;
}
Expand All @@ -180,7 +194,9 @@ class GH4252Address
{
/**
* @var int
* @Id @Column(type="integer") @GeneratedValue
* @Id
* @Column(type="integer")
* @GeneratedValue
*/
private $id;

Expand All @@ -195,17 +211,17 @@ public function __construct()
$this->flag = true;
}

public function getId() : int
public function getId(): int
{
return $this->id;
}

public function getFlag() : bool
public function getFlag(): bool
{
return $this->flag;
}

public function setFlag(bool $flag) : void
public function setFlag(bool $flag): void
{
$this->flag = $flag;
}
Expand Down

0 comments on commit 17bc1ad

Please sign in to comment.