共计 3871 个字符,预计需要花费 10 分钟才能阅读完成。
Golang 能够通过 Gorm 包来操作数据库,所谓 ORM,即 Object Relational Mapping(数据关系映射),说白了就是通过模式化的语法来操作数据库的行对象或者表对象,比照绝对灵便简约的 SQL 语句,ORM 上手简略,通用性较高,然而在性能层面略有损耗,Gorm 的底层是构造体对象,对于构造体,请移玉步至:你有对象类, 我有构造体,Go lang1.18 入门精炼教程,由白丁入鸿儒,go lang 构造体 (struct) 的应用 EP06。
Gorm 的装置与配置
首先如果要应用 Gorm 操作数据库,得先有数据库才行,这里为了全平台统一标准,咱们应用 Docker 来装置 Mysql 数据库,Docker 的装置请参见:一寸宕机一寸血,十万容器十万兵 |Win10/Mac 零碎下基于 Kubernetes(k8s)搭建 Gunicorn+Flask 高可用 Web 集群,运行命令运行 mysql 容器:
docker run --name mysql -p 3306:3306 -e MYSQL_ROOT_PASSWORD=root -d mysql:8.0.19
留神这里如果宿主机曾经有 Mysql 服务了,须要将: 右边的端口号错开,改成 3307 或者其余什么端口。
随后在终端运行命令装置 Gorm 包:
go get -u github.com/jinzhu/gorm
这里 - u 参数的意思是为以后用户装置,并不局限于某个我的项目。
随后装置 Mysql 数据库链接驱动包:
go get -u github.com/go-sql-driver/mysql
接着在任意地位编写 test.go 脚本:
package main
import (
"fmt"
"github.com/jinzhu/gorm"
_ "github.com/jinzhu/gorm/dialects/mysql"
)
func main() {db, err := gorm.Open("mysql", "root:root@(localhost)/mytest?charset=utf8mb4&parseTime=True&loc=Local")
if err != nil {fmt.Println(err)
fmt.Println("连贯数据库出错")
return
}
defer db.Close()
fmt.Println("链接 Mysql 胜利")
}
这里导入输入包和 Gorm 包,同时通过下划线的模式导入 mysql 驱动包,这样做的益处是 mysql 驱动的 init()函数会在被导入时执行,因为咱们并不需要驱动包的具体模块或者函数,而仅仅是用它连一下数据库而已。
随后,创立构造体变量 db,留神 Open 函数对应的 Mysql 参数是否正确。
留神,构造体变量赋值过程中如果报错,须要判断 err 变量内容,并且应用 return 关键字提前结束逻辑,对于 golang 的错误处理,可参见:人非圣贤孰能无过,Go lang1.18 入门精炼教程,由白丁入鸿儒,Go lang 错误处理机制 EP11
最初,应用 defer 关键字在所有逻辑执行后敞开 Mysql 数据库链接。
编译执行后,程序返回:
链接 Mysql 胜利
当然 Gorm 并不仅仅只能操作 Mysql,其余支流数据库也都反对,比方说 Sqllite3,事实上,在老本无限或者缓存体系比拟齐备的状况下,Sqllite3 齐全能够代替 Mysql,首先装置 sqllite3 驱动:
go get -u github.com/jinzhu/gorm/dialects/sqlite
而后批改 test.go 文件:
package main
import (
"fmt"
"github.com/jinzhu/gorm"
//_ "github.com/jinzhu/gorm/dialects/mysql"
_ "github.com/jinzhu/gorm/dialects/sqlite"
)
func main() {//db, err := gorm.Open("mysql", "root:root@(localhost)/mytest?charset=utf8mb4&parseTime=True&loc=Local")
db, err := gorm.Open("sqlite3", "/tmp/gorm.db")
if err != nil {fmt.Println(err)
fmt.Println("连贯数据库出错")
return
}
defer db.Close()
fmt.Println("链接 sqllite3 胜利")
}
编译执行后返回:
链接 sqllite3 胜利
数据库操作
连贯好数据库之后,咱们就能够做一些数据库层面的操作了,比方程序层面的数据库迁徙操作:
// 文章信息
type ArticleInfo struct {
ID uint
Title string
Author string
}
这里建设文章表的构造体数据,随后编写迁徙逻辑:
// 数据迁徙
db.AutoMigrate(&ArticleInfo{})
fmt.Println("表创立胜利")
进入 Mysql 命令行,输出命令:
MySQL [(none)]> use mytest;
Database changed
MySQL [mytest]> desc article_infos
-> ;
+--------+------------------+------+-----+---------+----------------+
| Field | Type | Null | Key | Default | Extra |
+--------+------------------+------+-----+---------+----------------+
| id | int(10) unsigned | NO | PRI | NULL | auto_increment |
| title | varchar(255) | YES | | NULL | |
| author | varchar(255) | YES | | NULL | |
+--------+------------------+------+-----+---------+----------------+
3 rows in set (0.03 sec)
MySQL [mytest]>
没有问题。
创立数据:
a1 := ArticleInfo{1, "iris", "iris"}
a2 := ArticleInfo{2, "iris", "女"}
// 创立记录
db.Create(&a1)
db.Create(&a2)
这里咱们申明两个构造体变量,而后将其指针传递给 db 变量的 Create 函数,编译运行后,键入命令进行查问操作:
MySQL [mytest]> select * from article_infos\g
+----+-------+--------+
| id | title | author |
+----+-------+--------+
| 1 | iris | iris |
| 2 | iris | 女 |
+----+-------+--------+
随后,将方才入库的数据查问进去:
// 查问
a := new(ArticleInfo)
db.First(a)
fmt.Println(a)
这里通过 new 关键字初始化构造体,而后应用 First 函数获取第一条记录。
程序返回:
链接 mysql 胜利
&{1 iris iris}
查出来的构造体指针能够间接用来做批改操作:
// 查问
a := new(ArticleInfo)
db.First(a)
fmt.Println(a)
// 批改
db.Model(&a).Update("Author", "123")
fmt.Println(a)
程序返回:
链接 mysql 胜利
&{1 iris iris}
&{1 iris 123}
十分不便。
最初,是删除操作:
// 删除
db.Delete(&a)
这里通过指针传入 Delete 函数即可:
MySQL [mytest]> select * from article_infos\g
+----+-------+--------+
| id | title | author |
+----+-------+--------+
| 2 | iris | 女 |
该条记录曾经被物理删除。
执行原生 SQL
如果咱们须要执行原生的 sql 语句,Gorm 也提供了对应的函数:
var articles []ArticleInfo
// 查问 执行用 Scan 和 Find 一样
db = db.Raw("select * from article_infos").Scan(&articles)
fmt.Println(articles)
这里只须要申明文章的构造体变量,而后执行 Scan 函数即可:
[{2 iris 女} {3 iris iris} {4 iris 女}]
这里会返回一个切片嵌套构造体的后果集。
除此之外,更新和删除操作:
// 更新和删除. 插入用 Exec
db = db.Exec("update article_infos set author='123'where id = 2")
fmt.Println("更新了", db.RowsAffected, "条数据")
db = db.Exec("delete from article_infos where id=4")
fmt.Println("更新了", db.RowsAffected, "条数据")
程序返回:
[]main.ArticleInfo 更新了 1 条数据
更新了 1 条数据
结语
目前 Golang 的比拟风行的 ORM 包除了 Gorm,还有 Xorm,比照 Python 数据库 ORM 的百花齐放,百家争鸣,Go lang 还有很长的一段路须要走,实在环境下的数据库操作也不仅仅是增删改查,更多操作请移步 Gorm 官网文档:https://gorm.io/zh\_CN/docs/