5.2 xorm
xorm是一个简单而强大的Go语言ORM库. 通过它可以使数据库操作非常简便。
在上一节讲过 http://github.com/go-sql-driver/mysql ,在使用过程发现其灵活太差,如仅查询某几个字段,还要单独再写个方法,crud相关操作复用性不好,如果想操作多个表,需要写一堆代码。xorm很好地解决了以上问题,并支持 http://github.com/go-sql-driver/mysql。
项目:https://github.com/go-xorm/xorm
官方文档:https://github.com/go-xorm/xorm/blob/master/README_CN.md
操作指南 :http://xorm.io/docs
安装
go get github.com/go-xorm/xorm
创建测试表:
CREATE TABLE `user` (
`id` int(10) NOT NULL COMMENT '主键',
`name` varchar(100) NOT NULL DEFAULT '' COMMENT '名字',
`ctime` int(11) NOT NULL DEFAULT '0' COMMENT '创建时间'
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
示例:
package main
import (
"fmt"
_ "github.com/go-sql-driver/mysql"
"github.com/go-xorm/xorm"
"strconv"
"time"
)
type User struct {
Id int64
Name string
Ctime int64
}
func main() {
var err error
engine, err := xorm.NewEngine("mysql", "root:123456@tcp(127.0.0.1:3306)/testdb?charset=utf8mb4&parseTime=true&&loc=Local")
//results, err := engine.Query("select * from user")
fmt.Println(err)
ctime := time.Now().Unix()
var users []User
var user User
for i := 0; i < 4; i++ {
user = User{Name: "jerry" + strconv.Itoa(i), Ctime: ctime}
users = append(users, user)
}
//插入
//单条
affected, err := engine.Insert(&user)
fmt.Println(affected)//user.Id 为插入数据主键
//多条,插入多条记录并且不使用批量插入,此时实际生成多条插入语句,每条记录均会自动赋予Id值。
affected, err = engine.Insert(&users)
fmt.Println(affected)
//更新
user = User{Name: "piter", Ctime: ctime}
affected, err = engine.ID(1).Update(&user)
// UPDATE user SET ... Where id = ?
affected, err = engine.Update(&user, &User{Name: "jerry1"})
//UPDATE user SET ... Where name = ?
//查询
//单条
user = User{}
has, err := engine.Where("name = ?", "jerry0").Desc("id").Get(&user)
//等价于
user = User{Name:"jerry0"}
has, err := engine.Desc("id").Get(&user)
// SELECT * FROM user WHERE name = ? ORDER BY id DESC LIMIT 1
fmt.Println(has)
fmt.Println(user)
var name string
has, err = engine.Table("user").Where("id = ?", 2).Cols("name").Get(&name)
// SELECT name FROM user WHERE id = ?
fmt.Println(has)
//多条
name = "jerry0"
err = engine.Where("name = ?", name).And("id > 1").Limit(10, 0).Find(&users)
fmt.Println(users)
//删除
//delete()
user = User{}
//user = User{Name: "Henry", Ctime: ctime}
affected, err = engine.Where("name=?", "piter").Delete(&user)
// DELETE FROM user Where ...
affected, err = engine.ID(2).Delete(&user)
//DELETE FROM user Where id = ?
fmt.Println(affected)
//事务
err = insert(engine)
}
func insert(engine *xorm.Engine) error {
ctime := time.Now().Unix()
session := engine.NewSession()
defer session.Close()
// add Begin() before any action
if err := session.Begin(); err != nil {
// if returned then will rollback automatically
return err
}
user1 := User{Name: "xiaoxiao", Ctime: ctime}
if _, err := session.Insert(&user1); err != nil {
fmt.Println(err)
return err
}
user2 := User{Name: "jerry0"}
if _, err := session.Where("id = ?", 2).Update(&user2); err != nil {
fmt.Println(err)
return err
}
if _, err := session.Exec("delete from user where name = ?", user2.Name); err != nil {
fmt.Println(err)
return err
}
// add Commit() after all actions
return session.Commit()
}
还有一个基于原版xorm的定制增强版本(xormplus/xorm),为xorm提供类似ibatis的配置文件及动态SQL支持,支持AcitveRecord操作。感兴趣的同学可以了解下。
xorm工具
使用Golang操作数据库的同学,经常遇到根据数据库表结构创建对应的struct模型,这个工作比较繁琐无味。那么,有没有工具自动生成这些代码呢?答案是肯定的。
xorm就自己带了这个工具。下面讲解xorm工具的使用:
xorm 是一组数据库操作命令行工具。
安装
有两种方式安装
1、二进制安装
如果你安装了 got,你可以输入如下命令安装:
got go-xorm/cmd/xorm
或者你可以从 gobuild 下载后解压到可执行路径。
2、源码安装
go get github.com/go-xorm/cmd/xorm
同时你需要安装如下依赖:
- github.com/go-xorm/xorm
- Mysql: github.com/go-sql-driver/mysql
- MyMysql: github.com/ziutek/mymysql/godrv
- Postgres: github.com/lib/pq
- SQLite: github.com/mattn/go-sqlite3
** 对于sqlite3的支持,你需要自己进行编译 go build -tags sqlite3
因为sqlite3需要cgo的支持。
这里我们采用源码安装,并以mysql 为例。
命令列表
有如下可用的命令:
reverse 反转一个数据库结构,生成代码
shell 通用的数据库操作客户端,可对数据库结构和数据操作
dump Dump数据库中所有结构和数据到标准输出
source 从标注输入中执行SQL文件
driver 列出所有支持的数据库驱动
示例
利用reverse 反转一个数据库结构,生成代码,
准备工作
先建一个数据库testdb,里面有表 member。
在$GOPATH/src 目录下创建 templates目录,
复制 $GOPATH/src/github.com/go-xorm/cmd/xorm/templates/goxorm 到 新建的templates目录下
cp $GOPATH/src/github.com/go-xorm/cmd/xorm/templates/goxorm $GOPATH/src/templates/ -rp
执行
xorm reverse mysql root:123456@tcp(127.0.0.1:3306)/testdb?charset=utf8mb4 $GOPATH/src/templates/goxorm [你想生成代码的目录,默认当前目录models,这里我们用默认]
如果成功的话,在$GOPATH/src/models目录下有个member.go,内容类似
package models
import (
"time"
)
type Member struct {
Id int64 `xorm:"pk autoincr comment('ID') BIGINT(20)"`
State int `xorm:"not null default 1 comment('状态') TINYINT(1)"`
Ctime int `xorm:"not null default 0 comment('注册时间') index INT(10)"`
Mtime time.Time `xorm:"not null default 'CURRENT_TIMESTAMP' comment('更新时间') index TIMESTAMP"`
Uname string `xorm:"not null comment('用户名') index VARCHAR(50)"`
Avatar string `xorm:"not null comment('头像') VARCHAR(255)"`
Passwd string `xorm:"not null default '‘’' comment('密码') VARCHAR(32)"`
Gender int `xorm:"not null default 1 comment('性别') TINYINT(1)"`
Birthday time.Time `xorm:"not null default '1990-01-10' comment('生日') DATE"`
Ip int64 `xorm:"not null default 0 comment('注册ip') BIGINT(20)"`
Ext string `xorm:"comment('扩展信息') TEXT"`
Market string `xorm:"not null comment('应用市场') VARCHAR(100)"`
Source string `xorm:"not null default 'reg' comment('来源 'crm', 'reg', 'green', 'robot'') index ENUM('crm','green','reg','robot')"`
}
Shell
Shell command provides a tool to operate database. For example, you can create table, alter table, insert data, delete data and etc.
xorm shell sqlite3 test.db
will connect to the sqlite3 database and you can type help
to list all the shell commands.
Dump
Dump command provides a tool to dump all database structs and data as SQL to your standard output.
xorm dump sqlite3 test.db
could dump sqlite3 database test.db to standard output. If you want to save to file, just type xorm dump sqlite3 test.db > test.sql
.
Source
xorm source sqlite3 test.db < test.sql
will execute sql file on the test.db.
Driver
List all supported drivers since default build will not include sqlite3.