一架梯子,一头程序猿,仰望星空!

Go migrate数据库版本管理

Go Migrate是一个用Go语言编写的用于管理数据库迁移的工具。它可以作为命令行接口(CLI)或导入为Go项目的库使用。

Go Migrate教程

1. Go Migrate概述

Go Migrate是一个用Go语言编写的用于管理数据库迁移的工具。它可以作为命令行接口(CLI)或导入为Go项目的库使用。Go Migrate可以从不同的源读取迁移文件,并按正确的顺序应用到数据库中。它支持各种数据库驱动和迁移源。

2. 版本

Go Migrate支持多个版本,包括:

  • Master:最新版本,包含新功能和错误修复
  • v4:稳定版本,适用于生产环境
  • v3:不再支持,不应使用

3. 安装

要使用Go Migrate,您需要安装Go包。运行以下命令进行安装:

go get -u -d github.com/golang-migrate/migrate/v4
cd $GOPATH/src/github.com/golang-migrate/migrate/v4

3. 使用Go Migrate

Go Migrate可以通过CLI或作为Go项目中的库来使用。

3.0. 数据库连接 URLs

无论是cli还是go代码使用,都需要配置database url,用于连接数据库。

URL格式:

dbdriver://username:password@host:port/dbname?param1=true&param2=false

这个URL是一个数据库连接URL,用于连接数据库并指定连接参数。下面是对每个部分的解释:

  1. dbdriver://:这是数据库驱动程序的协议标识符,用于指定使用哪个数据库驱动程序,例如:mysql。
  2. username:password:这是用于身份验证的用户名和密码。通常,用户名和密码之间使用冒号(:)分隔。
  3. @:这个符号用于将用户名和密码与主机名和端口号分隔开。
  4. host:port:这是数据库服务器的主机名和端口号。主机名是数据库服务器的IP地址或域名,端口号是数据库服务器监听的端口。
  5. /dbname:这是要连接的数据库的名称。
  6. ?param1=true&param2=false:这部分是查询参数,用于指定连接的额外参数。在这个例子中,有两个参数

这些查询参数可以根据具体的数据库驱动程序和数据库服务器的要求进行设置,用于配置连接的特定属性或行为。

postgres连接参数

postgres://postgres:password@localhost:5432/example?sslmode=disable

sqlite连接参数

sqlite3://path/to/database?query

mongodb连接参数

mongodb://user:password@host:port/dbname?query

3.1 CLI使用

3.1.1 基本用法

要使用CLI,请运行以下命令:

migrate -source file://path/to/migrations -database postgres://localhost:5432/database up 2

此命令将从指定的源应用迁移到给定的数据库。数字"2"表示要应用的迁移数量。

3.1.2 Docker使用

Go Migrate也可以与Docker一起使用。运行以下命令:

docker run -v {{ migration dir }}:/migrations --network host migrate/migrate -path=/migrations/ -database postgres://localhost:5432/database up 2

此命令在Docker容器中运行Go Migrate,并将指定源的迁移应用到给定的数据库。

3.2 在您的Go项目中使用

要在您的Go项目中使用Go Migrate,您需要导入所需的包和库。以下是一个示例:

import (
    "github.com/golang-migrate/migrate/v4"
    _ "github.com/golang-migrate/migrate/v4/database/postgres"
    _ "github.com/golang-migrate/migrate/v4/source/github"
)

func main() {
    m, err := migrate.New(
        "github://mattes:personal-access-token@mattes/migrate_test",
        "postgres://localhost:5432/database?sslmode=enable")
    m.Steps(2)
}

此代码使用指定的源和数据库初始化Go Migrate。然后使用Steps方法应用2个迁移。

如果您想使用现有的数据库客户端,请参照以下示例:

import (
    "database/sql"
    _ "github.com/lib/pq"
    "github.com/golang-migrate/migrate/v4"
    "github.com/golang-migrate/migrate/v4/database/postgres"
    _ "github.com/golang-migrate/migrate/v4/source/file"
)

func main() {
    db, err := sql.Open("postgres", "postgres://localhost:5432/database?sslmode=enable")
    driver, err := postgres.WithInstance(db, &postgres.Config{})
    m, err := migrate.NewWithDatabaseInstance(
        "file:///migrations",
        "postgres", driver)
    m.Up()
}

此代码导入所需的包,并使用sql包初始化数据库客户端。然后使用NewWithDatabaseInstance方法创建一个新的Go Migrate实例,指定源和数据库驱动。最后,使用Up方法应用迁移。

4. 支持的数据库驱动

Go Migrate支持多种数据库驱动,包括:

  • PostgreSQL
  • PGX v4
  • PGX v5
  • Redshift
  • Ql
  • Cassandra
  • SQLite
  • SQLite3
  • SQLCipher
  • MySQL/MariaDB
  • Neo4j
  • MongoDB
  • CrateDB
  • Shell
  • Google Cloud Spanner
  • CockroachDB
  • YugabyteDB
  • ClickHouse
  • Firebird
  • MS SQL Server

5. 支持迁移源

Go Migrate支持多个迁移源,包括:

  • 文件系统:从本地文件系统读取迁移。
  • io/fs:使用Go io/fs包读取迁移。
  • Go-Bindata:使用jteeuwen/go-bindata包从嵌入的二进制数据中读取迁移。
  • pkger:使用markbates/pkger包从嵌入的二进制数据中读取迁移。
  • GitHub:从远程GitHub仓库读取迁移。
  • GitHub企业版:从远程GitHub企业版仓库读取迁移。
  • Bitbucket:从远程Bitbucket仓库读取迁移。
  • Gitlab:从远程Gitlab仓库读取迁移。
  • AWS S3:从Amazon Web Services S3读取迁移。
  • Google Cloud Storage:从Google Cloud Platform Storage读取迁移。

你可以根据的项目需求,把数据库迁移文件存储在上面支持的文件存储源中。

6. 迁移文件

Go Migrate中的迁移文件具有特定的文件名格式和内容格式。

6.1 迁移文件名格式

每个迁移由一个“up”迁移文件和一个对应的“down”迁移文件组成。迁移的文件名应符合以下格式:

{version}_{title}.up.{extension}
{version}_{title}.down.{extension}

version是表示迁移应该应用的顺序的唯一数字。title是迁移的可选描述。extension取决于所使用的数据库系统(例如,对于SQL变体,使用.sql)。

6.2 迁移内容格式

迁移文件的内容因数据库系统而异,通常就是直接写SQL

例如下面两个迁移文本:

  • 000001_create_users_table.up.sql
  • 000001_create_users_table.down.sql

迁移文件000001_create_users_table.up.sql

CREATE TABLE IF NOT EXISTS users(
   user_id serial PRIMARY KEY,
   username VARCHAR (50) UNIQUE NOT NULL,
   password VARCHAR (50) NOT NULL,
   email VARCHAR (300) UNIQUE NOT NULL
);

迁移文件 000001_create_users_table.down.sql, down文件主要是撤销前面的操作,通常用于回滚

DROP TABLE IF EXISTS users;

6.3 迁移的可逆性

编写可逆迁移是最佳实践。这意味着应该能够同时运行迁移的上升和下降到任何版本,从而有效地重新创建和清理数据库状态。

为确保可逆性,每个迁移应有一个对应的“up”和“down”迁移文件。“up”迁移文件包含应用迁移的操作,而“down”迁移文件包含撤销迁移的操作。

7. MySQL的用法

Go Migrate提供对MySQL数据库的支持。要连接到MySQL数据库,需要使用以下格式的数据库URL:

mysql://user:password@tcp(host:port)/dbname?query

URL可以包含查询参数,如迁移表的名称、TLS参数等。有关查询参数的完整列表,请参阅Go Migrate MySQL文档

7.1 URL查询参数

  • x-migrations-table:迁移表的名称。
  • x-no-lock:设置为true以跳过GET_LOCK/RELEASE_LOCK语句。对于多主MySQL版本很有用。
  • x-statement-timeout:中止超过指定毫秒数的任何语句。
  • dbname:要连接的数据库的名称。
  • user:要登录的用户。
  • password:用户的密码。
  • host:要连接的主机。
  • port:要绑定的端口。
  • tls:TLS/SSL加密连接参数。
  • x-tls-ca:CA(证书授权机构)文件的位置。
  • x-tls-cert:客户端证书文件的位置。
  • x-tls-key:私钥文件的位置。
  • x-tls-insecure-skip-verify:是否使用SSL。

7.2 与现有客户端一起使用

如果你希望将Go Migrate与现有的MySQL客户端一起使用,请确保在创建客户端时使用multiStatements=true参数。以下是一个示例:

package main

import (
    "database/sql"
    
    _ "github.com/go-sql-driver/mysql"
    "github.com/golang-migrate/migrate/v4"
    "github.com/golang-migrate/migrate/v4/database/mysql"
    _ "github.com/golang-migrate/migrate/v4/source/file"
)

func main() {
    db, _ := sql.Open("mysql", "user:password@tcp(host:port)/dbname?multiStatements=true")
    driver, _ := mysql.WithInstance(db, &mysql.Config{})
    m, _ := migrate.NewWithDatabaseInstance(
        "file:///migrations",
        "mysql", 
        driver,
    )
    
    m.Steps(2)
}

该代码导入所需的包,创建一个MySQL数据库客户端,并使用数据库实例初始化Go Migrate。然后,通过Steps方法应用了两个迁移。

章节目录