English | 中文
Dcmigrate is a database migration tool based on Gorm, which complements the Gorm migration mechanism without any functional conflicts, aiming to provide a more user-friendly database migration tool
- Supports mysql, sqlite, postgres, sqlserver, tidb, clickhouse and other databases
- Command line tool
- Depends on gorm
- Supports executing migration files in steps
- Supports rollback function
- Can view migration list and status
- Explicit "up" and "down" function implementation
- Supports repairing migration records
- The current version is still gradually iterating, please ensure continuous feature upgrades**
go get -u github.com/fanqie/dcmigrate
This is the directory structure you obtained after initializing the project
example/
├── dmc.go // This is the command-line tool for dcmigration
├── dc_migrations // This is the migration file directory for dcmigration
└── register.go // This is the migration file registration file for dcmigration, which is automatically generated and maintained by dcmigration. Please do not manually modify it
└── 20230301_000000_create_users_table.go // This is the migration file for dcmigration
├── go.mod
├── go.sum
└── ... you project files
You must complete the initialization operation
go run .\dmc.go --help
[Info]check dc_migrations table
[Info]dc_migrations is ok
Usage:
[command]
Available Commands:
completion Generate the autocompletion script for the specified shell
gen generate a new core file
syntax:dmc gen [--create|--alter] {table_name}
usage:`dmc gen --create user` //or `dmc gen --alter user`
help Help about any command
list show all migrations record
migrate all new migration file versions will be migrated or target step size version
rollback rollback history migrates
syntax:dmc rollback [--step=1] [--all] {table_name}
usage:`dmc rollback --step=2` //or `dmc rollback --all`
Flags:
-h, --help help for this command
Use " [command] --help" for more information about a command.
If you use 'go run' when running the project` To start, there may be command line conflicts due to two 'funcmain()' appearing in the root directory at the same time.
You can resolve this issue by:
//When a conflict occurs, you can directly specify the entry file name to run your project, for example:
//Go run [project entry file. go]
go run main.go
// go run app.go
// go run entry.go
// ...
Open the "dmc. go" file, modify the database connection information, and then run the dmc. go file. You can configure the database connection according to the reference code and the official Gorm documentation
Gorm Connecting Database Doc Guide
package main
import (
"github.com/fanqie/dcmigrate-example/dc_migrations"
"github.com/fanqie/dcmigrate/pkg"
"github.com/fanqie/dcmigrate/pkg/core"
"gorm.io/driver/mysql"
"gorm.io/gorm"
"gorm.io/gorm/logger"
)
func main() {
dcMigrate := pkg.NewDcMigrate(true)
dc_migrations.Register(dcMigrate)
dcMigrate.Setup(core.GromParams{
Dialector: mysqlDialector(),
// or ↓↓↓↓↓↓↓↓↓↓
//Dialector: sqliteDialector(),
//Dialector: pgsqlDialector(),
//Dialector: sqlserverDialector(),
//Dialector: tiDBDialector(),
//Dialector: clickhouseDialector(),
Opts: &gorm.Config{
Logger: logger.Default.LogMode(logger.Error),
},
}, func() {
})
}
// connecting_to_the_database more doc: https://gorm.io/docs/connecting_to_the_database.html
func mysqlDialector() gorm.Dialector {
dsn := "root:root@tcp(127.0.0.1:3306)/test?charset=utf8mb4&parseTime=True&loc=Local"
return mysql.Open(dsn)
}
// go get -u gorm.io/driver/sqlite
//func sqliteDialector() gorm.Dialector {
// dsn := "test.db"
// return sqlite.Open(dsn)
//}
// go get -u gorm.io/driver/postgres
//func pgsqlDialector() gorm.Dialector {
// dsn := "user=root password=root dbname=test port=6943 sslmode=disable TimeZone=Local"
// return postgres.Open(dsn)
//}
// sqlserver
// go get -u gorm.io/driver/sqlserver
//func sqlserverDialector() gorm.Dialector {
// dsn := "sqlserver://gorm:LoremIpsum86@localhost:9930?database=gorm"
// return sqlserver.Open(dsn)
//}
// TiDB
// go get -u gorm.io/driver/mysql
//func tiDBDialector() gorm.Dialector {
// dsn := "root:@tcp(127.0.0.1:4000)/test"
// return mysql.Open(dsn)
//}
// Clickhouse
// go get -u gorm.io/driver/clickhouse
//func clickhouseDialector() gorm.Dialector {
// dsn := "tcp://localhost:9000?database=gorm&username=gorm&password=gorm&read_timeout=10&write_timeout=20"
// return clickhouse.Open(dsn)
//}
go run dmc.go gen --create users
[Info]check dc_migrations table
[Success]create dc_migrations
[Success]ok!
[Info]create migration start
[Success]ok! file name :[./dc_migrations/migration_v_2025_02_14_09_48_00_702_create_table_users.go]
go run dmc.go gen --alter users
# output
[Info]check dc_migrations table
[Info]dc_migrations is ok
[Info]create migration start
[Success]ok! file name :[./dc_migrations/migration_v_2025_02_14_09_55_03_505_alter_table_users.go]
go run dmc.go list
[Info]check dc_migrations table
[Info]dc_migrations is ok
┌────┬──────────────────────────────────────────────┬─────────────────────┬─────────────────┐
│ ID │ TAG │ CREATEDAT │ ALREADYMIGRATED │
├────┼──────────────────────────────────────────────┼─────────────────────┼─────────────────┤
│ 3 │ v_2025_02_14_13_50_55_793_create_table_users │ 2025-02-14 13:50:55 │ ☑ Yes! │
│ 5 │ v_2025_02_14_14_05_56_456_alter_table_users │ 2025-02-14 14:05:56 │ Pending │
└────┴──────────────────────────────────────────────┴─────────────────────┴─────────────────┘
go run dmc.go migrate
# output
[Info]check dc_migrations table
[Info]dc_migrations is ok
[Info]migration start
[Info]migration:V20250214094800702CreateTableUsers
[Success]migration count: 0 version: V20250214094800702CreateTableUsers ok!
[Info]migration:V20250214095503505AlterTableUsers
[Success]migration count: 0 version: V20250214095503505AlterTableUsers ok!
[Info]migration done, handle count: 2
go run dmc.go migrate --step=1
# output
[Info]check dc_migrations table
[Info]dc_migrations is ok
[Info]migration start
[Info]migration:V20250214094800702CreateTableUsers
[Success]migration count: 1 version: V20250214094800702CreateTableUsers ok!
[Info]migration done, handle count: 1
go run dmc.go rollback --step=1
# output
[Info]check dc_migrations table
[Info]dc_migrations is ok
[Info]rollback start
[Info]rollback(1):V20250214095503505AlterTableUsers
[Success]rollback count:1 version: V20250214095503505AlterTableUsers ok!
[Info]rollback done, handle count: 1
go run dmc.go rollback --all
# output
[Info]check dc_migrations table
[Info]dc_migrations is ok
[Info]rollback start
[Info]rollback(99999999):V20250214095503505AlterTableUsers
[Success]rollback count:99999999 version: V20250214095503505AlterTableUsers ok!
[Info]rollback(99999999):V20250214094800702CreateTableUsers
[Success]rollback count:99999999 version: V20250214094800702CreateTableUsers ok!
[Info]rollback done, handle count: 2
When the migration table cannot be migrated correctly due to operational errors, this command can be used
If there are any issues with the status, it needs to be manually modified in the database
go run dmc.go repair
[Info]check dc_migrations table
[Info]dc_migrations is ok
[Info]Fix unmatched items start
[Success]Fix unmatched items count:0
[Info]Fix missing items start
[Success]Fix missing items count:0
[Warning]If there are any issues with the status, it needs to be manually modified in the database
[Success]repair ok!
id | tag | already_migrated | created_at | updated_at | executed_at | reverted_at |
---|---|---|---|---|---|---|
1 | v_2025_02_14_09_48_00_702_create_table_users | 1 | 2025-02-14 09:48:00.976 | 2025-02-14 10:05:20.698 | 2025-02-14 10:05:20.698 | 2025-02-14 10:04:50.403 |
2 | v_2025_02_14_09_55_03_505_alter_table_users | 0 | 2025-02-14 09:55:03.022 | 2025-02-14 10:04:50.392 | 2025-02-14 10:04:36.251 | 2025-02-14 10:04:50.392 |
$ tree example/
example/
├── dmc.go
├── go.mod
├── go.sum
└── dc_migrations
├── migration_v_2025_02_14_09_48_00_702_create_table_users.go
├── migration_v_2025_02_14_09_55_03_505_alter_table_users.go
└── register.go
$ cat example/dc_migrations/register.go
package dc_migrations
import (
"github.com/fanqie/dcmigrate/pkg"
)
func Register(migrate *pkg.DcMigrate) {
migrate.RegisterMigration("V20250214094800702CreateTableUsers", NewMigrateV20250214094800702CreateTableUsers())
migrate.RegisterMigration("V20250214095503505AlterTableUsers", NewMigrateV20250214095503505AlterTableUsers())
}
USE test;
SHOW TABLES;
Tables in test |
---|
dc_migrations |
users |