Skip to content

Commit abd3c24

Browse files
authored
Merge pull request #88 from cycle/bugfix/table-inheritance
Improving table and database name searching
2 parents d3f62a7 + 2c64506 commit abd3c24

2 files changed

Lines changed: 73 additions & 11 deletions

File tree

src/TableInheritance.php

Lines changed: 37 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@
77
use Cycle\Annotated\Annotation\Inheritance;
88
use Cycle\Annotated\Exception\AnnotationException;
99
use Cycle\Annotated\Utils\EntityUtils;
10+
use Cycle\Schema\Definition\Entity;
1011
use Cycle\Schema\Definition\Entity as EntitySchema;
1112
use Cycle\Schema\Definition\Inheritance\JoinedTable as JoinedTableInheritanceSchema;
1213
use Cycle\Schema\Definition\Inheritance\SingleTable as SingleTableInheritanceSchema;
@@ -57,8 +58,8 @@ public function run(Registry $registry): Registry
5758
$childClass = $parent->getClass();
5859
} while ($this->parseMetadata($parent, Inheritance::class) !== null);
5960

60-
if ($entity = $this->initInheritance($annotation, $child, $parent)) {
61-
$found[] = $entity;
61+
if ($inheritanceEntity = $this->initInheritance($annotation, $child, $parent)) {
62+
$found[] = $inheritanceEntity;
6263
}
6364
}
6465

@@ -67,17 +68,10 @@ public function run(Registry $registry): Registry
6768
if (!$registry->hasEntity($child->getRole())) {
6869
$registry->register($child);
6970

70-
$database = $child->getDatabase();
71-
$tableName = $child->getTableName();
72-
if ($entity->getInheritance() instanceof SingleTableInheritanceSchema) {
73-
$database = $parent->getDatabase();
74-
$tableName = $parent->getTableName();
75-
}
76-
7771
$registry->linkTable(
7872
$child,
79-
$database,
80-
$tableName,
73+
$this->getDatabase($child, $registry),
74+
$this->getTableName($child, $registry)
8175
);
8276
}
8377
}
@@ -285,4 +279,36 @@ private function getOuterFields(
285279

286280
return $parent->getPrimaryFields();
287281
}
282+
283+
private function getTableName(Entity $child, Registry $registry): string
284+
{
285+
$parent = $this->findParent($registry, $this->utils->findParent($child->getClass(), false));
286+
287+
$inheritance = $parent->getInheritance();
288+
if (!$inheritance instanceof SingleTableInheritanceSchema) {
289+
return $child->getTableName();
290+
}
291+
$entities = \array_map(
292+
static fn (string $role) => $registry->getEntity($role)->getClass(),
293+
$inheritance->getChildren()
294+
);
295+
296+
return \in_array($child->getClass(), $entities, true) ? $parent->getTableName() : $child->getTableName();
297+
}
298+
299+
private function getDatabase(Entity $child, Registry $registry): ?string
300+
{
301+
$parent = $this->findParent($registry, $this->utils->findParent($child->getClass(), false));
302+
303+
$inheritance = $parent->getInheritance();
304+
if (!$inheritance instanceof SingleTableInheritanceSchema) {
305+
return $child->getDatabase();
306+
}
307+
$entities = \array_map(
308+
static fn (string $role) => $registry->getEntity($role)->getClass(),
309+
$inheritance->getChildren()
310+
);
311+
312+
return \in_array($child->getClass(), $entities, true) ? $parent->getDatabase() : $child->getDatabase();
313+
}
288314
}

tests/Annotated/Functional/Driver/Common/InheritanceTest.php

Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,8 @@
1212
use Cycle\Annotated\Tests\Fixtures\Fixtures16\Ceo;
1313
use Cycle\Annotated\Tests\Fixtures\Fixtures16\Customer;
1414
use Cycle\Annotated\Tests\Fixtures\Fixtures16\Employee;
15+
use Cycle\Annotated\Tests\Fixtures\Fixtures16\Executive;
16+
use Cycle\Annotated\Tests\Fixtures\Fixtures16\Person;
1517
use Cycle\ORM\SchemaInterface;
1618
use Cycle\Schema\Compiler;
1719
use Cycle\Schema\Generator\GenerateRelations;
@@ -21,7 +23,9 @@
2123
use Cycle\Schema\Generator\ResetTables;
2224
use Cycle\Schema\Generator\SyncTables;
2325
use Cycle\Schema\Registry;
26+
use Spiral\Attributes\AttributeReader;
2427
use Spiral\Attributes\ReaderInterface;
28+
use Spiral\Tokenizer\ClassesInterface;
2529
use Spiral\Tokenizer\Config\TokenizerConfig;
2630
use Spiral\Tokenizer\Tokenizer;
2731

@@ -128,4 +132,36 @@ public function testTableInheritance(ReaderInterface $reader): void
128132
'hidden' => 'hidden',
129133
], $schema['beaver'][SchemaInterface::COLUMNS]);
130134
}
135+
136+
public function testTableInheritanceWithIncorrectClassesOrder(): void
137+
{
138+
$r = new Registry($this->dbal);
139+
$reader = new AttributeReader();
140+
$locator = $this->createMock(ClassesInterface::class);
141+
$locator
142+
->method('getClasses')
143+
->willReturn([
144+
new \ReflectionClass(Employee::class),
145+
new \ReflectionClass(Executive::class),
146+
new \ReflectionClass(Person::class),
147+
]);
148+
149+
$schema = (new Compiler())->compile($r, [
150+
new Embeddings($locator, $reader),
151+
new Entities($locator, $reader),
152+
new TableInheritance($reader),
153+
new ResetTables(),
154+
new MergeColumns($reader),
155+
new GenerateRelations(),
156+
new RenderTables(),
157+
new RenderRelations(),
158+
new MergeIndexes($reader),
159+
new SyncTables(),
160+
new GenerateTypecast(),
161+
]);
162+
163+
$this->assertSame('executives', $schema['executive'][SchemaInterface::TABLE]);
164+
$this->assertNull($schema['employee'][SchemaInterface::TABLE] ?? null);
165+
$this->assertSame('people', $schema['person'][SchemaInterface::TABLE]);
166+
}
131167
}

0 commit comments

Comments
 (0)