官方文档:https://gorm.io/zh_CN/docs/connecting_to_the_database.html

最简单的连接方法

通过一行 DSN 连接

1
2
dsn := "user:pass@tcp(127.0.0.1:3306)/dbname?charset=utf8mb4&parseTime=True&loc=Local"
db, err := gorm.Open(mysql.Open(dsn), &gorm.Config{})

示例

1
2
3
4
5
6
7
8
9
10
11
12
13
package main

import (
"fmt"
"gorm.io/driver/mysql"
"gorm.io/gorm"
)

func main() {
dsn := "root:1234@tcp(127.0.0.1:3306)/gorm_learning?charset=utf8mb4&parseTime=True&loc=Local"
db, err := gorm.Open(mysql.Open(dsn), &gorm.Config{})
fmt.Println(db, err)
}

image-20220930174718178

可见没有返回错误


配置连接参数

gorm.Open() 方法有两个参数,分别可以对数据库和 GORM 进行更高级的配置

mysql.Config

这样可以设置一些高级配置

1
2
3
4
5
6
7
8
db, err := gorm.Open(mysql.New(mysql.Config{
DSN: "gorm:gorm@tcp(127.0.0.1:3306)/gorm?charset=utf8&parseTime=True&loc=Local", // DSN data source name
DefaultStringSize: 256, // string 类型字段的默认长度
DisableDatetimePrecision: true, // 禁用 datetime 精度,MySQL 5.6 之前的数据库不支持
DontSupportRenameIndex: true, // 重命名索引时采用删除并新建的方式,MySQL 5.7 之前的数据库和 MariaDB 不支持重命名索引
DontSupportRenameColumn: true, // 用 `change` 重命名列,MySQL 8 之前的数据库和 MariaDB 不支持重命名列
SkipInitializeWithVersion: false, // 根据当前 MySQL 版本自动配置
}), &gorm.Config{})

更多的可以配置的项目可以点进去看源码,或者去看文档

gorm.Config

这个自己去看官方文档吧,感觉还是挺详细的

1
2
3
4
5
6
7
8
9
10
11
12
type Config struct {
SkipDefaultTransaction bool
NamingStrategy schema.Namer
Logger logger.Interface
NowFunc func() time.Time
DryRun bool
PrepareStmt bool
DisableNestedTransaction bool
AllowGlobalUpdate bool
DisableAutomaticPing bool
DisableForeignKeyConstraintWhenMigrating bool
}

比较重点的有命名策略,这个可以更改你创建的表名,增加些前缀后缀什么的

然后还有最后一个 DisableForeignKeyConstraintWhenMigrating 是否要跳过外键约束,这个建议跳过

因为这个交给数据库检查的话代价很高,建议自己在代码逻辑自动体现外键关系(逻辑外键)

示例:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
package main

import (
"fmt"
"gorm.io/driver/mysql"
"gorm.io/gorm"
"gorm.io/gorm/schema"
)

func main() {
db, err := gorm.Open(mysql.New(mysql.Config{
DSN: "root:1234@tcp(127.0.0.1:3306)/gorm_learning?charset=utf8mb4&parseTime=True&loc=Local", // DSN data source name
DefaultStringSize: 191, // string 类型字段的默认长度
DisableDatetimePrecision: true, // 禁用 datetime 精度,MySQL 5.6 之前的数据库不支持
DontSupportRenameIndex: true, // 重命名索引时采用删除并新建的方式,MySQL 5.7 之前的数据库和 MariaDB 不支持重命名索引
DontSupportRenameColumn: true, // 用 `change` 重命名列,MySQL 8 之前的数据库和 MariaDB 不支持重命名列
SkipInitializeWithVersion: false, // 根据当前 MySQL 版本自动配置
}),前 *gorm.DB 返回一个通 &gorm.Config{
NamingStrategy: schema.NamingStrategy{
TablePrefix: "t_", // 表名前缀,`User` 的表名应该是 `t_users`
SingularTable: true, // 使用单数表名,启用该选项,此时,`User` 的表名应该是 `t_user`
},
DisableForeignKeyConstraintWhenMigrating: true,
})
fmt.Println(db, err)
}


使用连接池

与数据库连接时可以使用连接池,关于连接池可以看这篇 Golang 侧数据库连接池原理和参数调优

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
sqlDB, err := db.DB()

// SetMaxIdleConns 设置空闲连接池中连接的最大数量
sqlDB.SetMaxIdleConns(10)

// SetMaxOpenConns 设置打开数据库连接的最大数量。
sqlDB.SetMaxOpenConns(100)

// SetConnMaxLifetime 设置了连接可复用的最大时间。
sqlDB.SetConnMaxLifetime(time.Hour)

// 获取 gorm db,其他包调用此方法即可拿到 db
// 无需担心不同协程并发时使用这个 db 对象会公用一个连接,因为 db 在调用其方法时候会从数据库连接池获取新的连接
func GetDB() *gorm.DB {
return db
}