Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit 8eb6992

Browse files
authored
Merge pull request #10809 from mpdude/show-trouble-delete-before-insert
Add test to show why delete-before-insert may be challenging
2 parents 7ef4afc + e9b6fd8 commit 8eb6992

1 file changed

Lines changed: 158 additions & 0 deletions

File tree

Lines changed: 158 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,158 @@
1+
<?php
2+
3+
declare(strict_types=1);
4+
5+
namespace Doctrine\Tests\ORM\Functional\Ticket;
6+
7+
use Doctrine\Common\Collections\ArrayCollection;
8+
use Doctrine\Common\Collections\Collection;
9+
use Doctrine\ORM\Mapping as ORM;
10+
use Doctrine\Tests\OrmFunctionalTestCase;
11+
12+
class GH5742Test extends OrmFunctionalTestCase
13+
{
14+
protected function setUp(): void
15+
{
16+
parent::setUp();
17+
18+
$this->createSchemaForModels(
19+
GH5742Person::class,
20+
GH5742Toothbrush::class,
21+
GH5742ToothpasteBrand::class
22+
);
23+
}
24+
25+
public function testUpdateOneToOneToNewEntityBeforePreviousEntityCanBeRemoved(): void
26+
{
27+
$person = new GH5742Person();
28+
$oldToothbrush = new GH5742Toothbrush();
29+
$person->toothbrush = $oldToothbrush;
30+
31+
$this->_em->persist($person);
32+
$this->_em->persist($oldToothbrush);
33+
$this->_em->flush();
34+
35+
$oldToothbrushId = $oldToothbrush->id;
36+
37+
$newToothbrush = new GH5742Toothbrush();
38+
$person->toothbrush = $newToothbrush;
39+
40+
$this->_em->remove($oldToothbrush);
41+
$this->_em->persist($newToothbrush);
42+
43+
// The flush operation will have to make sure the new toothbrush
44+
// has been written to the database
45+
// _before_ the person can be updated to refer to it.
46+
// Likewise, the update must have happened _before_ the old
47+
// toothbrush can be removed (non-nullable FK constraint).
48+
49+
$this->_em->flush();
50+
51+
$this->_em->clear();
52+
self::assertSame($newToothbrush->id, $this->_em->find(GH5742Person::class, $person->id)->toothbrush->id);
53+
self::assertNull($this->_em->find(GH5742Toothbrush::class, $oldToothbrushId));
54+
}
55+
56+
public function testManyToManyCollectionUpdateBeforeRemoval(): void
57+
{
58+
$person = new GH5742Person();
59+
$person->toothbrush = new GH5742Toothbrush(); // to satisfy not-null constraint
60+
$this->_em->persist($person);
61+
62+
$oldMice = new GH5742ToothpasteBrand();
63+
$this->_em->persist($oldMice);
64+
65+
$person->preferredBrands->set(1, $oldMice);
66+
$this->_em->flush();
67+
68+
$oldBrandId = $oldMice->id;
69+
70+
$newSpice = new GH5742ToothpasteBrand();
71+
$this->_em->persist($newSpice);
72+
73+
$person->preferredBrands->set(1, $newSpice);
74+
75+
$this->_em->remove($oldMice);
76+
77+
// The flush operation will have to make sure the new brand
78+
// has been written to the database _before_ it can be referred
79+
// to from the m2m join table.
80+
// Likewise, the old join table entry must have been removed
81+
// _before_ the old brand can be removed.
82+
83+
$this->_em->flush();
84+
85+
$this->_em->clear();
86+
self::assertCount(1, $this->_em->find(GH5742Person::class, $person->id)->preferredBrands);
87+
self::assertNull($this->_em->find(GH5742ToothpasteBrand::class, $oldBrandId));
88+
}
89+
}
90+
91+
/**
92+
* @ORM\Entity
93+
*/
94+
class GH5742Person
95+
{
96+
/**
97+
* @ORM\Id
98+
* @ORM\GeneratedValue(strategy="AUTO")
99+
* @ORM\Column(type="integer")
100+
*
101+
* @var int
102+
*/
103+
public $id;
104+
105+
/**
106+
* @ORM\OneToOne(targetEntity="GH5742Toothbrush", cascade={"persist"})
107+
* @ORM\JoinColumn(nullable=false)
108+
*
109+
* @var GH5742Toothbrush
110+
*/
111+
public $toothbrush;
112+
113+
/**
114+
* @ORM\ManyToMany(targetEntity="GH5742ToothpasteBrand")
115+
* @ORM\JoinTable(name="gh5742person_gh5742toothpastebrand",
116+
* joinColumns={@ORM\JoinColumn(name="person_id", referencedColumnName="id", onDelete="CASCADE")},
117+
* inverseJoinColumns={@ORM\JoinColumn(name="brand_id", referencedColumnName="id")}
118+
* )
119+
*
120+
* @var Collection<GH5742ToothpasteBrand>
121+
*/
122+
public $preferredBrands;
123+
124+
public function __construct()
125+
{
126+
$this->preferredBrands = new ArrayCollection();
127+
}
128+
}
129+
130+
/**
131+
* @ORM\Entity
132+
*/
133+
class GH5742Toothbrush
134+
{
135+
/**
136+
* @ORM\Id
137+
* @ORM\GeneratedValue(strategy="AUTO")
138+
* @ORM\Column(type="integer")
139+
*
140+
* @var int
141+
*/
142+
public $id;
143+
}
144+
145+
/**
146+
* @ORM\Entity
147+
*/
148+
class GH5742ToothpasteBrand
149+
{
150+
/**
151+
* @ORM\Id
152+
* @ORM\GeneratedValue(strategy="AUTO")
153+
* @ORM\Column(type="integer")
154+
*
155+
* @var int
156+
*/
157+
public $id;
158+
}

0 commit comments

Comments
 (0)