Skip to content

Commit 53bbf08

Browse files
committed
Implementation in progress + add more tests
1 parent 4f3efe9 commit 53bbf08

File tree

5 files changed

+400
-47
lines changed

5 files changed

+400
-47
lines changed

src/lib/migrations/BaseMigrationBuilder.php

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -544,7 +544,14 @@ abstract public function handleColumnsPositionsChanges(array $haveNames, array $
544544

545545

546546
/**
547-
* TODO docs
547+
* Only for MySQL and MariaDB
548+
* Given a column, compute its previous column name present in OpenAPI schema
549+
* @param ColumnSchema $column
550+
* @param bool $forDrop
551+
* @return ?string
552+
* `null` if column is added at last
553+
* 'FIRST' if column is added at first position
554+
* 'AFTER <columnName>' if column is added in between e.g. if 'email' is added after 'username' then 'AFTER username'
548555
*/
549556
abstract public function findPosition(ColumnSchema $column, bool $forDrop = false): ?string;
550557
}

src/lib/migrations/MigrationRecordBuilder.php

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -115,15 +115,15 @@ public function addDbColumn(string $tableAlias, ColumnSchema $column, ?string $p
115115
public function alterColumn(string $tableAlias, ColumnSchema $column, ?string $position = null):string # TODO
116116
{
117117
if (property_exists($column, 'xDbType') && is_string($column->xDbType) && !empty($column->xDbType)) {
118-
$converter = $this->columnToCode($tableAlias, $column, true, false, true, true);
118+
$converter = $this->columnToCode($tableAlias, $column, true, false, true, true, $position);
119119
return sprintf(
120120
ApiGenerator::isPostgres() ? self::ALTER_COLUMN_RAW_PGSQL : self::ALTER_COLUMN_RAW,
121121
$tableAlias,
122122
$column->name,
123123
ColumnToCode::escapeQuotes($converter->getCode())
124124
);
125125
}
126-
$converter = $this->columnToCode($tableAlias, $column, true);
126+
$converter = $this->columnToCode($tableAlias, $column, true, false, false, false, $position);
127127
return sprintf(self::ALTER_COLUMN, $tableAlias, $column->name, $converter->getCode(true));
128128
}
129129

src/lib/migrations/MysqlMigrationBuilder.php

Lines changed: 54 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -23,16 +23,32 @@ final class MysqlMigrationBuilder extends BaseMigrationBuilder
2323
*/
2424
protected function buildColumnChanges(ColumnSchema $current, ColumnSchema $desired, array $changed):void
2525
{
26+
$positionCurrent = $positionDesired = null;
27+
if (in_array('position', $changed, true)) {
28+
$positionCurrent = $this->findPosition($current, true);
29+
$positionDesired = $this->findPosition($desired);
30+
$key = array_search('position', $changed, true);
31+
if ($key !== false) {
32+
unset($changed[$key]);
33+
}
34+
}
2635
$newColumn = clone $current;
27-
$position = $this->findPosition($desired);
36+
// $positionCurrent = $this->findPosition($desired, true);
37+
// $positionDesired = $this->findPosition($desired);
38+
// if ($positionCurrent === $positionDesired) {
39+
// $positionCurrent = $positionDesired = null;
40+
// } # else {
41+
// $position = $positionDesired;
42+
// $newColumn->position = $position;
43+
// }
2844
foreach ($changed as $attr) {
2945
$newColumn->$attr = $desired->$attr;
3046
}
3147
if (static::isEnum($newColumn)) {
3248
$newColumn->dbType = 'enum'; // TODO this is concretely not correct
3349
}
34-
$this->migration->addUpCode($this->recordBuilder->alterColumn($this->model->getTableAlias(), $newColumn, $position))
35-
->addDownCode($this->recordBuilder->alterColumn($this->model->getTableAlias(), $current, $position));
50+
$this->migration->addUpCode($this->recordBuilder->alterColumn($this->model->getTableAlias(), $newColumn, $positionDesired))
51+
->addDownCode($this->recordBuilder->alterColumn($this->model->getTableAlias(), $current, $positionCurrent));
3652
}
3753

3854
protected function compareColumns(ColumnSchema $current, ColumnSchema $desired):array
@@ -67,6 +83,14 @@ protected function compareColumns(ColumnSchema $current, ColumnSchema $desired):
6783
}
6884
}
6985
}
86+
87+
$positionCurrent = $this->findPosition($desired, true);
88+
$positionDesired = $this->findPosition($desired);
89+
90+
if ($positionCurrent !== $positionDesired) {
91+
$changedAttributes[] = 'position';
92+
}
93+
7094
return $changedAttributes;
7195
}
7296

@@ -168,31 +192,8 @@ public function checkOrder()
168192
{
169193
}
170194

171-
// TODO
172-
public function handleColumnsPositionsChanges(array $haveNames, array $wantNames)
173-
{
174-
$indices = [];
175-
if ($haveNames !== $wantNames) {
176-
foreach ($wantNames as $key => $name) {
177-
if ($name !== $haveNames[$key]) {
178-
$indices[] = $key;
179-
}
180-
}
181-
}
182-
for ($i = 0; $i < count($indices) / 2; $i++) {
183-
$this->migration->addUpCode($this->recordBuilder->alterColumn());
184-
}
185-
}
186-
187-
188195
/**
189-
* TODO move this method to MysqlMigrationBuilder
190-
* Only for MySQL and MariaDB
191-
* Given a column, compute its previous column name present in OpenAPI schema
192-
* @return ?string
193-
* `null` if column is added at last
194-
* 'FIRST' if column is added at first position
195-
* 'AFTER <columnName>' if column is added in between e.g. if 'email' is added after 'username' then 'AFTER username'
196+
* {@inheritDoc}
196197
*/
197198
public function findPosition(ColumnSchema $column, bool $forDrop = false): ?string
198199
{
@@ -218,4 +219,30 @@ public function findPosition(ColumnSchema $column, bool $forDrop = false): ?stri
218219

219220
return null;
220221
}
222+
223+
224+
// TODO
225+
public function handleColumnsPositionsChanges(array $haveNames, array $wantNames)
226+
{
227+
$indices = [];
228+
if ($haveNames !== $wantNames) {
229+
foreach ($wantNames as $key => $name) {
230+
if ($name !== $haveNames[$key]) {
231+
$indices[] = $key;
232+
}
233+
}
234+
}
235+
for ($i = 0; $i < count($indices) / 2; $i++) {
236+
$this->migration->addUpCode($this->recordBuilder->alterColumn(
237+
$this->model->getTableAlias(),
238+
$this->newColumns[$wantNames[$indices[$i]]],
239+
$this->findPosition($this->newColumns[$wantNames[$indices[$i]]])
240+
))->addDownCode($this->recordBuilder->alterColumn(
241+
$this->model->getTableAlias(),
242+
$this->tableSchema->columns[$wantNames[$indices[$i]]],
243+
$this->findPosition($this->tableSchema->columns[$wantNames[$indices[$i]]], true)
244+
));
245+
}
246+
// $this->migration->addUpCode($this->recordBuilder->dropTable($this->model->getTableAlias()));
247+
}
221248
}

tests/specs/issue_fix/58_create_migration_for_column_position_change_if_a_field_position_is_changed_in_spec/index.yml

Lines changed: 4 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -11,13 +11,10 @@ components:
1111
properties:
1212
id:
1313
type: integer
14-
# name: # TODO
15-
# type: string
16-
# description: desc
17-
# colour:
18-
# type: string
19-
# description:
20-
# type: string
14+
name:
15+
type: string
16+
description:
17+
type: string
2118

2219
paths:
2320
'/':

0 commit comments

Comments
 (0)