mirror of
https://github.com/Syngnat/GoNavi.git
synced 2026-07-13 00:13:33 +08:00
- PostgreSQL 类数据库 DROP DATABASE 自动切换到维护库执行 - 避免前端传入目标库名时被误判为当前连接正在使用 - 同步修复 ALTER DATABASE RENAME 的同类误判 - 补充 PostgreSQL 删除和重命名数据库回归测试 Close #567
227 lines
7.9 KiB
Go
227 lines
7.9 KiB
Go
package app
|
|
|
|
import (
|
|
"testing"
|
|
|
|
"GoNavi-Wails/internal/connection"
|
|
"GoNavi-Wails/internal/db"
|
|
"GoNavi-Wails/internal/secretstore"
|
|
)
|
|
|
|
type fakeRenameDatabaseDB struct {
|
|
connectConfig connection.ConnectionConfig
|
|
execQueries []string
|
|
}
|
|
|
|
func (f *fakeRenameDatabaseDB) Connect(config connection.ConnectionConfig) error {
|
|
f.connectConfig = config
|
|
return nil
|
|
}
|
|
func (f *fakeRenameDatabaseDB) Close() error { return nil }
|
|
func (f *fakeRenameDatabaseDB) Ping() error { return nil }
|
|
func (f *fakeRenameDatabaseDB) Query(query string) ([]map[string]interface{}, []string, error) {
|
|
return nil, nil, nil
|
|
}
|
|
func (f *fakeRenameDatabaseDB) Exec(query string) (int64, error) {
|
|
f.execQueries = append(f.execQueries, query)
|
|
return 0, nil
|
|
}
|
|
func (f *fakeRenameDatabaseDB) GetDatabases() ([]string, error) { return nil, nil }
|
|
func (f *fakeRenameDatabaseDB) GetTables(dbName string) ([]string, error) {
|
|
return nil, nil
|
|
}
|
|
func (f *fakeRenameDatabaseDB) GetCreateStatement(dbName, tableName string) (string, error) {
|
|
return "", nil
|
|
}
|
|
func (f *fakeRenameDatabaseDB) GetColumns(dbName, tableName string) ([]connection.ColumnDefinition, error) {
|
|
return nil, nil
|
|
}
|
|
func (f *fakeRenameDatabaseDB) GetAllColumns(dbName string) ([]connection.ColumnDefinitionWithTable, error) {
|
|
return nil, nil
|
|
}
|
|
func (f *fakeRenameDatabaseDB) GetIndexes(dbName, tableName string) ([]connection.IndexDefinition, error) {
|
|
return nil, nil
|
|
}
|
|
func (f *fakeRenameDatabaseDB) GetForeignKeys(dbName, tableName string) ([]connection.ForeignKeyDefinition, error) {
|
|
return nil, nil
|
|
}
|
|
func (f *fakeRenameDatabaseDB) GetTriggers(dbName, tableName string) ([]connection.TriggerDefinition, error) {
|
|
return nil, nil
|
|
}
|
|
|
|
var _ db.Database = (*fakeRenameDatabaseDB)(nil)
|
|
|
|
func TestResolveDDLDBType_DorisTypeAlias(t *testing.T) {
|
|
if got := resolveDDLDBType(connection.ConnectionConfig{Type: "doris"}); got != "diros" {
|
|
t.Fatalf("expected Doris type alias to resolve to diros, got %q", got)
|
|
}
|
|
}
|
|
|
|
func TestRenameDatabase_DorisUsesNativeRenameSQL(t *testing.T) {
|
|
originalNewDatabaseFunc := newDatabaseFunc
|
|
originalResolveDialConfigWithProxyFunc := resolveDialConfigWithProxyFunc
|
|
t.Cleanup(func() {
|
|
newDatabaseFunc = originalNewDatabaseFunc
|
|
resolveDialConfigWithProxyFunc = originalResolveDialConfigWithProxyFunc
|
|
})
|
|
|
|
fakeDB := &fakeRenameDatabaseDB{}
|
|
newDatabaseFunc = func(dbType string) (db.Database, error) {
|
|
return fakeDB, nil
|
|
}
|
|
resolveDialConfigWithProxyFunc = func(raw connection.ConnectionConfig) (connection.ConnectionConfig, error) {
|
|
return raw, nil
|
|
}
|
|
|
|
app := NewAppWithSecretStore(secretstore.NewUnavailableStore("test"))
|
|
result := app.RenameDatabase(connection.ConnectionConfig{
|
|
Type: "custom",
|
|
Driver: "doris",
|
|
Database: "orders",
|
|
}, "orders", "orders_new")
|
|
|
|
if !result.Success {
|
|
t.Fatalf("expected Doris rename success, got failure: %s", result.Message)
|
|
}
|
|
if len(fakeDB.execQueries) != 1 {
|
|
t.Fatalf("expected one rename statement, got %d: %#v", len(fakeDB.execQueries), fakeDB.execQueries)
|
|
}
|
|
const want = "ALTER DATABASE `orders` RENAME `orders_new`"
|
|
if fakeDB.execQueries[0] != want {
|
|
t.Fatalf("unexpected Doris rename SQL, want %q got %q", want, fakeDB.execQueries[0])
|
|
}
|
|
}
|
|
|
|
func TestResolvePGLikeDatabaseDDLRunConfig_UsesCompatibleMaintenanceDatabase(t *testing.T) {
|
|
kingbase := resolvePGLikeDatabaseDDLRunConfig(connection.ConnectionConfig{
|
|
Type: "kingbase",
|
|
User: "system",
|
|
Database: "test",
|
|
}, "kingbase", "test")
|
|
if kingbase.Database != "template1" {
|
|
t.Fatalf("expected Kingbase target test to use template1 maintenance database, got %q", kingbase.Database)
|
|
}
|
|
|
|
vastbase := resolvePGLikeDatabaseDDLRunConfig(connection.ConnectionConfig{
|
|
Type: "vastbase",
|
|
User: "vastbase",
|
|
Database: "tenant_db",
|
|
}, "vastbase", "tenant_db")
|
|
if vastbase.Database != "vastbase" {
|
|
t.Fatalf("expected Vastbase target tenant_db to use vastbase maintenance database, got %q", vastbase.Database)
|
|
}
|
|
}
|
|
|
|
func TestDropDatabase_PostgresUsesMaintenanceDatabaseWhenConfigTargetsDroppedDB(t *testing.T) {
|
|
originalNewDatabaseFunc := newDatabaseFunc
|
|
originalResolveDialConfigWithProxyFunc := resolveDialConfigWithProxyFunc
|
|
t.Cleanup(func() {
|
|
newDatabaseFunc = originalNewDatabaseFunc
|
|
resolveDialConfigWithProxyFunc = originalResolveDialConfigWithProxyFunc
|
|
})
|
|
|
|
fakeDB := &fakeRenameDatabaseDB{}
|
|
newDatabaseFunc = func(dbType string) (db.Database, error) {
|
|
return fakeDB, nil
|
|
}
|
|
resolveDialConfigWithProxyFunc = func(raw connection.ConnectionConfig) (connection.ConnectionConfig, error) {
|
|
return raw, nil
|
|
}
|
|
|
|
app := NewAppWithSecretStore(secretstore.NewUnavailableStore("test"))
|
|
result := app.DropDatabase(connection.ConnectionConfig{
|
|
Type: "postgres",
|
|
Host: "127.0.0.1",
|
|
Port: 5432,
|
|
User: "postgres",
|
|
Database: "test",
|
|
}, "test")
|
|
|
|
if !result.Success {
|
|
t.Fatalf("expected PostgreSQL drop database success, got failure: %s", result.Message)
|
|
}
|
|
if fakeDB.connectConfig.Database != "postgres" {
|
|
t.Fatalf("expected PostgreSQL drop database to connect to maintenance database postgres, got %q", fakeDB.connectConfig.Database)
|
|
}
|
|
if len(fakeDB.execQueries) != 1 {
|
|
t.Fatalf("expected one drop statement, got %d: %#v", len(fakeDB.execQueries), fakeDB.execQueries)
|
|
}
|
|
const want = `DROP DATABASE "test"`
|
|
if fakeDB.execQueries[0] != want {
|
|
t.Fatalf("unexpected PostgreSQL drop SQL, want %q got %q", want, fakeDB.execQueries[0])
|
|
}
|
|
}
|
|
|
|
func TestDropDatabase_PostgresUsesTemplateWhenDroppingPostgresDatabase(t *testing.T) {
|
|
originalNewDatabaseFunc := newDatabaseFunc
|
|
originalResolveDialConfigWithProxyFunc := resolveDialConfigWithProxyFunc
|
|
t.Cleanup(func() {
|
|
newDatabaseFunc = originalNewDatabaseFunc
|
|
resolveDialConfigWithProxyFunc = originalResolveDialConfigWithProxyFunc
|
|
})
|
|
|
|
fakeDB := &fakeRenameDatabaseDB{}
|
|
newDatabaseFunc = func(dbType string) (db.Database, error) {
|
|
return fakeDB, nil
|
|
}
|
|
resolveDialConfigWithProxyFunc = func(raw connection.ConnectionConfig) (connection.ConnectionConfig, error) {
|
|
return raw, nil
|
|
}
|
|
|
|
app := NewAppWithSecretStore(secretstore.NewUnavailableStore("test"))
|
|
result := app.DropDatabase(connection.ConnectionConfig{
|
|
Type: "postgres",
|
|
Host: "127.0.0.1",
|
|
Port: 5432,
|
|
User: "postgres",
|
|
Database: "postgres",
|
|
}, "postgres")
|
|
|
|
if !result.Success {
|
|
t.Fatalf("expected PostgreSQL drop database success, got failure: %s", result.Message)
|
|
}
|
|
if fakeDB.connectConfig.Database != "template1" {
|
|
t.Fatalf("expected PostgreSQL drop postgres database to connect to template1, got %q", fakeDB.connectConfig.Database)
|
|
}
|
|
}
|
|
|
|
func TestRenameDatabase_PostgresUsesMaintenanceDatabaseWhenConfigTargetsRenamedDB(t *testing.T) {
|
|
originalNewDatabaseFunc := newDatabaseFunc
|
|
originalResolveDialConfigWithProxyFunc := resolveDialConfigWithProxyFunc
|
|
t.Cleanup(func() {
|
|
newDatabaseFunc = originalNewDatabaseFunc
|
|
resolveDialConfigWithProxyFunc = originalResolveDialConfigWithProxyFunc
|
|
})
|
|
|
|
fakeDB := &fakeRenameDatabaseDB{}
|
|
newDatabaseFunc = func(dbType string) (db.Database, error) {
|
|
return fakeDB, nil
|
|
}
|
|
resolveDialConfigWithProxyFunc = func(raw connection.ConnectionConfig) (connection.ConnectionConfig, error) {
|
|
return raw, nil
|
|
}
|
|
|
|
app := NewAppWithSecretStore(secretstore.NewUnavailableStore("test"))
|
|
result := app.RenameDatabase(connection.ConnectionConfig{
|
|
Type: "postgres",
|
|
Host: "127.0.0.1",
|
|
Port: 5432,
|
|
User: "postgres",
|
|
Database: "test",
|
|
}, "test", "test_new")
|
|
|
|
if !result.Success {
|
|
t.Fatalf("expected PostgreSQL rename database success, got failure: %s", result.Message)
|
|
}
|
|
if fakeDB.connectConfig.Database != "postgres" {
|
|
t.Fatalf("expected PostgreSQL rename database to connect to maintenance database postgres, got %q", fakeDB.connectConfig.Database)
|
|
}
|
|
if len(fakeDB.execQueries) != 1 {
|
|
t.Fatalf("expected one rename statement, got %d: %#v", len(fakeDB.execQueries), fakeDB.execQueries)
|
|
}
|
|
const want = `ALTER DATABASE "test" RENAME TO "test_new"`
|
|
if fakeDB.execQueries[0] != want {
|
|
t.Fatalf("unexpected PostgreSQL rename SQL, want %q got %q", want, fakeDB.execQueries[0])
|
|
}
|
|
}
|