golang数据库迁移生成工具插件sqlize的使用
Golang数据库迁移生成工具插件sqlize的使用
SQLize是一个强大的迁移生成工具,可以检测两个SQL状态源之间的差异。它通过比较现有的SQL模式和Go模型来简化迁移创建,确保无缝的数据库更新。
特性
- 支持MySQL、PostgreSQL和SQLite
- 与流行的Go ORM和迁移工具集成,如gorm、golang-migrate/migrate等
- 提供高级功能,包括Avro Schema导出(仅MySQL)和ERD图生成(MermaidJS)
默认行为
- 数据库:mysql(使用
sql_builder.WithPostgresql()
切换为PostgreSQL等) - SQL语法:大写(如
"SELECT * FROM user WHERE id = ?"
)- 使用
sql_builder.WithSqlLowercase()
切换为小写
- 使用
- 表命名:单数形式
- 使用
sql_builder.WithPluralTableName()
切换为复数形式(添加’s’)
- 使用
- 注释生成:使用
sql_builder.WithCommentGenerate()
SQL标签选项
type User struct {
ID int `sql:"primary_key"` // 主键
Name string `sql:"column:user_name"` // 自定义列名
Email string `sql:"unique"` // 唯一索引
Age int `sql:"default:18"` // 默认值
CreatedAt string `sql:"type:TIMESTAMP"` // 覆盖数据类型
Status string `sql:"-"` // 忽略字段
AddressID int `sql:"foreign_key:address_id;references:id"` // 外键
}
完整示例
package main
import (
"fmt"
"log"
"os"
"github.com/sunary/sqlize"
)
// 定义模型结构体
type User struct {
ID int `sql:"primary_key"`
Name string `sql:"column:user_name"`
Email string `sql:"unique"`
Age int `sql:"default:18"`
CreatedAt string `sql:"type:TIMESTAMP"`
}
// 实现YourModels函数返回模型切片
func YourModels() []interface{} {
return []interface{}{
&User{},
}
}
func main() {
migrationFolder := "migrations/"
sqlLatest := sqlize.NewSqlize(sqlize.WithSqlTag("sql"),
sqlize.WithMigrationFolder(migrationFolder),
sqlize.WithCommentGenerate())
ms := YourModels()
err := sqlLatest.FromObjects(ms...)
if err != nil {
log.Fatal("sqlize FromObjects", err)
}
sqlVersion := sqlLatest.HashValue()
sqlMigrated := sqlize.NewSqlize(sqlize.WithMigrationFolder(migrationFolder))
err = sqlMigrated.FromMigrationFolder()
if err != nil {
log.Fatal("sqlize FromMigrationFolder", err)
}
sqlLatest.Diff(*sqlMigrated)
fmt.Println("sql version", sqlVersion)
fmt.Println("\n\n### migration up")
migrationUp := sqlLatest.StringUp()
fmt.Println(migrationUp)
fmt.Println("\n\n### migration down")
fmt.Println(sqlLatest.StringDown())
// 写入迁移文件
if len(os.Args) > 1 {
log.Println("write to file", os.Args[1])
err = sqlLatest.WriteFilesWithVersion(os.Args[1], sqlVersion, false)
if err != nil {
log.Fatal("sqlize WriteFilesWithVersion", err)
}
}
}
数据类型处理
MySQL数据类型会隐式转换:
TINYINT => tinyint(4)
INT => int(11)
BIGINT => bigint(20)
指针值必须在结构体中声明或预定义数据类型:
type Record struct {
ID int
DeletedAt *time.Time `sql:"type:DATETIME"` // 预定义类型
}
// 或使用database/sql支持的struct
type Record struct {
ID int
DeletedAt sql.NullTime
}
SQLize是一个功能强大的工具,可以大大简化Golang项目中的数据库迁移工作。通过比较模型和现有数据库结构,自动生成迁移脚本,确保数据库模式与代码模型保持同步。
更多关于golang数据库迁移生成工具插件sqlize的使用的实战教程也可以访问 https://www.itying.com/category-94-b0.html
1 回复
更多关于golang数据库迁移生成工具插件sqlize的使用的实战系列教程也可以访问 https://www.itying.com/category-94-b0.html
SQLize - Golang数据库迁移生成工具
SQLize 是一个用于Golang的数据库迁移工具,它可以帮助你管理数据库架构的变更。下面我将详细介绍SQLize的使用方法和示例代码。
安装SQLize
首先,使用go get命令安装SQLize:
go get -u github.com/sunary/sqlize
基本概念
SQLize 提供了两种主要功能:
- 从现有数据库生成迁移文件
- 从Golang结构体生成迁移文件
使用示例
1. 从现有数据库生成迁移
package main
import (
"log"
"github.com/sunary/sqlize"
)
func main() {
// 创建SQLize实例
sqlizer := sqlize.NewSqlize(sqlize.WithMigrationFolder("./migrations"))
// 从数据库生成迁移文件
err := sqlizer.FromDb("mysql", "user:password@tcp(127.0.0.1:3306)/database_name")
if err != nil {
log.Fatal(err)
}
// 生成迁移文件
err = sqlizer.DumpMigrationFiles()
if err != nil {
log.Fatal(err)
}
log.Println("迁移文件生成成功")
}
2. 从Golang结构体生成迁移
package main
import (
"log"
"github.com/sunary/sqlize"
)
type User struct {
ID int64 `sql:"primary_key;auto_increment"`
Name string `sql:"type:varchar(100);not null"`
Email string `sql:"type:varchar(100);unique;not null"`
CreatedAt int64 `sql:"type:bigint;not null"`
UpdatedAt int64 `sql:"type:bigint;not null"`
}
type Post struct {
ID int64 `sql:"primary_key;auto_increment"`
Title string `sql:"type:varchar(255);not null"`
Content string `sql:"type:text"`
UserID int64 `sql:"type:bigint;not null;index"`
}
func main() {
// 创建SQLize实例
sqlizer := sqlize.NewSqlize(
sqlize.WithMigrationFolder("./migrations"),
sqlize.WithSqlTag("sql"),
)
// 添加模型
sqlizer.AddModels(
User{},
Post{},
)
// 生成迁移文件
err := sqlizer.DumpMigrationFiles()
if err != nil {
log.Fatal(err)
}
log.Println("迁移文件生成成功")
}
3. 自定义迁移文件名
sqlizer := sqlize.NewSqlize(
sqlize.WithMigrationFolder("./migrations"),
sqlize.WithMigrationName("create_user_and_post_tables"),
)
4. 使用现有迁移文件
sqlizer := sqlize.NewSqlize(
sqlize.WithMigrationFolder("./migrations"),
sqlize.WithMigrationTable("migrations"), // 自定义迁移表名
sqlize.WithMigrationUp(true), // 只生成up迁移
sqlize.WithMigrationDown(false), // 不生成down迁移
)
高级功能
1. 自定义模板
sqlizer := sqlize.NewSqlize(
sqlize.WithMigrationFolder("./migrations"),
sqlize.WithMigrationTemplate(
sqlize.MigrationTemplate{
Up: "/* up migration */\n{{.SqlUp}}",
Down: "/* down migration */\n{{.SqlDown}}",
},
),
)
2. 使用不同的方言
sqlizer := sqlize.NewSqlize(
sqlize.WithMigrationFolder("./migrations"),
sqlize.WithDialect(sqlize.Postgres), // 支持MySQL, Postgres, SQLite
)
3. 合并多个模型变更
sqlizer := sqlize.NewSqlize(
sqlize.WithMigrationFolder("./migrations"),
)
// 第一次添加模型
sqlizer.AddModels(User{})
// 第二次添加模型
sqlizer.AddModels(Post{})
// 生成一个包含所有变更的迁移文件
err := sqlizer.DumpMigrationFiles()
最佳实践
- 版本控制:将生成的迁移文件纳入版本控制系统
- 小步提交:每次架构变更生成单独的迁移文件
- 测试迁移:在生产环境应用前测试迁移脚本
- 备份数据:在执行破坏性迁移前备份数据
- 文档化:为复杂迁移添加注释说明
注意事项
- SQLize 主要用于生成迁移文件,不直接执行迁移
- 对于生产环境,建议使用专门的迁移工具(如golang-migrate)来执行迁移
- 复杂的数据库变更(如数据迁移)可能需要手动编写迁移脚本
SQLize 是一个强大的工具,可以显著简化Golang项目中的数据库迁移管理。通过结构体定义自动生成迁移文件,可以保持代码和数据库架构的同步,减少手动编写SQL脚本的错误。