add a way to change indexes with migrations without alter table

This commit is contained in:
Garth 2024-08-04 01:51:03 +02:00
parent 6bf4ad4b9e
commit 9e34773962
8 changed files with 196 additions and 2 deletions

View file

@ -14,4 +14,9 @@ abstract class Schema {
void createIfNotExists(String tableName, void Function(Table table) callback);
void alter(String tableName, void Function(MutableTable table) callback);
void indexes(
String tableName,
void Function(MutableIndexes indexes) callback,
);
}

View file

@ -43,14 +43,24 @@ abstract class Table {
}
}
abstract class MutableTable extends Table {
abstract class MutableTable extends Table implements MutableIndexes {
void rename(String newName);
void dropColumn(String name);
void renameColumn(String name, String newName);
void changeColumnType(String name, ColumnType type);
void dropNotNull(String name);
void setNotNull(String name);
}
abstract class MutableIndexes {
void addIndex(String name, List<String> columns, IndexType type);
void dropIndex(String name);
void dropPrimaryIndex();
}

View file

@ -1,4 +1,5 @@
import 'dart:async';
import 'package:angel3_migration/angel3_migration.dart';
import 'package:logging/logging.dart';
import 'package:mysql1/mysql1.dart';
@ -74,4 +75,12 @@ class MariaDbSchema extends Schema {
void createIfNotExists(
String tableName, void Function(Table table) callback) =>
_create(tableName, callback, true);
@override
void indexes(String tableName, void Function(MutableIndexes index) callback) {
var tbl = MariaDbIndexes(tableName);
callback(tbl);
tbl.compile(_buf);
}
}

View file

@ -229,3 +229,53 @@ class MariaDbAlterTable extends Table implements MutableTable {
_stack.add('DROP PRIMARY KEY');
}
}
class MariaDbIndexes implements MutableIndexes {
final String tableName;
final Queue<String> _stack = Queue<String>();
MariaDbIndexes(this.tableName);
void compile(StringBuffer buf) {
while (_stack.isNotEmpty) {
var str = _stack.removeFirst();
buf.writeln(str);
}
}
@override
void addIndex(String name, List<String> columns, IndexType type) {
// mask the column names, is more safety
columns = columns.map((column) => '`$column`').toList();
switch (type) {
case IndexType.primaryKey:
_stack.add(
'ALTER TABLE `$tableName` ADD PRIMARY KEY (${columns.join(',')});',
);
break;
case IndexType.unique:
_stack.add(
'CREATE UNIQUE INDEX IF NOT EXISTS `$name` '
'ON `$tableName` (${columns.join(',')});',
);
break;
case IndexType.standardIndex:
case IndexType.none:
_stack.add(
'CREATE INDEX `$name` ON `$tableName` (${columns.join(',')});',
);
break;
}
}
@override
void dropIndex(String name) {
_stack.add('DROP INDEX IF EXISTS `$name` ON `$tableName`;');
}
@override
void dropPrimaryIndex() {
_stack.add('DROP INDEX `PRIMARY` ON `$tableName`;');
}
}

View file

@ -1,4 +1,5 @@
import 'dart:async';
import 'package:angel3_migration/angel3_migration.dart';
import 'package:logging/logging.dart';
import 'package:mysql_client/mysql_client.dart';
@ -79,4 +80,12 @@ class MySqlSchema extends Schema {
void createIfNotExists(
String tableName, void Function(Table table) callback) =>
_create(tableName, callback, true);
@override
void indexes(String tableName, void Function(MutableIndexes table) callback) {
var tbl = MysqlIndexes(tableName);
callback(tbl);
tbl.compile(_buf);
}
}

View file

@ -235,3 +235,52 @@ class MysqlAlterTable extends Table implements MutableTable {
_stack.add('DROP PRIMARY KEY');
}
}
class MysqlIndexes implements MutableIndexes {
final String tableName;
final Queue<String> _stack = Queue<String>();
MysqlIndexes(this.tableName);
void compile(StringBuffer buf) {
while (_stack.isNotEmpty) {
buf.writeln(_stack.removeFirst());
}
}
@override
void addIndex(String name, List<String> columns, IndexType type) {
// mask the column names, is more safety
columns.map((column) => '`$column`');
switch (type) {
case IndexType.primaryKey:
_stack.add(
'ALTER TABLE `$tableName` ADD PRIMARY KEY (${columns.join(',')});',
);
break;
case IndexType.unique:
_stack.add(
'CREATE UNIQUE INDEX `$name` ON `$tableName` (${columns.join(',')});',
);
break;
case IndexType.standardIndex:
case IndexType.none:
default:
_stack.add(
'CREATE INDEX `$name` ON `$tableName` (${columns.join(',')});',
);
break;
}
}
@override
void dropIndex(String name) {
_stack.add('DROP INDEX `$name` ON `$tableName`;');
}
@override
void dropPrimaryIndex() {
_stack.add('DROP INDEX `PRIMARY` ON `$tableName`;');
}
}

View file

@ -1,7 +1,9 @@
import 'dart:async';
import 'package:angel3_migration/angel3_migration.dart';
import 'package:postgres/postgres.dart';
import 'package:logging/logging.dart';
import 'package:postgres/postgres.dart';
import 'table.dart';
/// A PostgreSQL database schema generator
@ -73,4 +75,12 @@ class PostgresSchema extends Schema {
void createIfNotExists(
String tableName, void Function(Table table) callback) =>
_create(tableName, callback, true);
@override
void indexes(String tableName, void Function(MutableIndexes table) callback) {
var tbl = PostgresIndexes(tableName);
callback(tbl);
tbl.compile(_buf);
}
}

View file

@ -176,6 +176,7 @@ class PostgresAlterTable extends Table implements MutableTable {
indexType = 'PRIMARY KEY';
break;
case IndexType.unique:
// ??
indexType = 'CONSTRAINT "$name" UNIQUE';
break;
case IndexType.standardIndex:
@ -200,3 +201,54 @@ class PostgresAlterTable extends Table implements MutableTable {
_stack.add('DROP CONSTRAINT "${tableName}_pkey"');
}
}
class PostgresIndexes implements MutableIndexes {
final String tableName;
final Queue<String> _stack = Queue<String>();
PostgresIndexes(this.tableName);
void compile(StringBuffer buf) {
while (_stack.isNotEmpty) {
buf.writeln(_stack.removeFirst());
}
}
@override
void addIndex(String name, List<String> columns, IndexType type) {
// mask the column names, is more safety
columns.map((column) => '"$column"');
switch (type) {
case IndexType.primaryKey:
_stack.add(
'ALTER TABLE "$tableName" ADD PRIMARY KEY (${columns.join(',')});',
);
break;
case IndexType.unique:
_stack.add(
'CREATE UNIQUE INDEX IF NOT EXISTS "$name" '
'ON "$tableName" (${columns.join(',')});',
);
break;
case IndexType.standardIndex:
case IndexType.none:
default:
_stack.add(
'CREATE INDEX IF NOT EXISTS "$name" '
'ON "$tableName" (${columns.join(',')});',
);
break;
}
}
@override
void dropIndex(String name) {
_stack.add('DROP INDEX "$name";');
}
@override
void dropPrimaryIndex() {
_stack.add('ALTER TABLE "$tableName" DROP CONSTRAINT "${tableName}_pkey"');
}
}