feat: 支持 Option<T> 字段(None↔NULL)、列命名默认原样(Keep)、迁移同名列先删后加,版本 1.1.0

This commit is contained in:
2026-08-21 03:41:53 +08:00
parent 132aae865b
commit 394c4a1fb5
14 changed files with 335 additions and 87 deletions
+44 -5
View File
@@ -48,11 +48,30 @@ public class Migrator {
m.up(builder)
let factory = DdlFactory()
for (op in builder.operations) {
let stmt = conn.prepareStatement(factory.toSql(op, _dialect))
try {
stmt.update()
} finally {
stmt.close()
let sqls = ArrayList<String>()
let isColumnOp = match (op.kind) {
case MigrationOperationKind.AddColumn |
MigrationOperationKind.AlterColumn => true
case _ => false
}
if (isColumnOp) {
// 同名列类型变更时先删后加(见 DdlFactory.resolveColumnSqls
let col = op.column.getOrThrow()
let resolved = factory.resolveColumnSqls(op, _dialect,
columnTypeInDb(conn, op.tableName, col.name))
for (s in resolved) {
sqls.add(s)
}
} else {
sqls.add(factory.toSql(op, _dialect))
}
for (sql in sqls) {
let stmt = conn.prepareStatement(sql)
try {
stmt.update()
} finally {
stmt.close()
}
}
}
recordApplied(conn, m)
@@ -153,6 +172,26 @@ public class Migrator {
}
}
/// 查询库中某列的数据类型(information_schema.data_type);列不存在返回 None。
/// 执行 addColumn/alterColumn 前调用,用于识别"同名列修改数据结构"场景。
private func columnTypeInDb(conn: Connection, table: String, column: String): ?String {
let stmt = conn.prepareStatement(
"SELECT data_type FROM information_schema.columns WHERE table_schema = current_schema() " +
"AND table_name = ? AND column_name = ?")
try {
stmt.set<String>(0, table)
stmt.set<String>(1, column)
let rs = stmt.query()
if (rs.next()) {
rs.getOrNull<String>(0)
} else {
None
}
} finally {
stmt.close()
}
}
private func resolveTarget(appliedList: ArrayList<Migration>, target: String): Int64 {
var exact: Int64 = -1
let prefixHits = ArrayList<Int64>()