Skip to content

Repository files navigation

Gorm-plus

基于 Gorm-plus,详见https://github.com/acmestack/gorm-plus

Gorm-plus是基于Gorm的增强版,类似Mybatis-plus语法。

特性

  • 无侵入,只做增强不做改变
  • 强大的CRUD 操作,内置通用查询,不需要任何配置,即可构建复杂条件查询
  • 支持指针字段形式查询,方便编写各类查询条件,无需再担心字段写错
  • 支持主键自动生成
  • 内置分页插件

事务(未发版)

  • 在需要事务的场景,可以使用gplus.Begin()开启事务,获取*gorm.DB
  • 所有的dao方法,均支持传入*gorm.DB,后续的操作均以传入的为准

预览

typeStudentstruct {
IDintNamestringAgeuint8EmailstringBirthday time.TimeCreatedAt time.TimeUpdatedAt time.Time
}
vargormDb*gorm.DBfuncinit() {
dsn:="root:123456@tcp(127.0.0.1:3306)/test?charset=utf8mb4&parseTime=True&loc=Local"varerrerrorgormDb, err=gorm.Open(mysql.Open(dsn), &gorm.Config{
Logger: logger.Default.LogMode(logger.Info),
})
iferr!=nil {
log.Println(err)
}
gplus.Init(gormDb)
}
funcmain() {
varstudentStudent// 创建表gormDb.AutoMigrate(student)
// 插入数据studentItem:=Student{Name: "zhangsan", Age: 18, Email: "123@11.com", Birthday: time.Now()}
gplus.Insert(&studentItem)
// 根据Id查询数据studentResult, resultDb:= gplus.SelectById[Student](studentItem.ID)
log.Printf("error:%v\n", resultDb.Error)
log.Printf("RowsAffected:%v\n", resultDb.RowsAffected)
log.Printf("studentResult:%+v\n", studentResult)
// 根据条件查询query, model:=gplus.NewQuery[Student]()
query.Eq(&model.Name, "zhangsan")
studentResult, resultDb=gplus.SelectOne(query)
log.Printf("error:%v\n", resultDb.Error)
log.Printf("RowsAffected:%v\n", resultDb.RowsAffected)
log.Printf("studentResult:%+v\n", studentResult)
// 根据Id更新studentItem.Name="lisi"resultDb= gplus.UpdateById[Student](&studentItem)
log.Printf("error:%v\n", resultDb.Error)
log.Printf("RowsAffected:%v\n", resultDb.RowsAffected)
// 根据条件更新query, model=gplus.NewQuery[Student]()
query.Eq(&model.Name, "lisi").Set(&model.Age, 35)
resultDb= gplus.Update[Student](query)
log.Printf("error:%v\n", resultDb.Error)
log.Printf("RowsAffected:%v\n", resultDb.RowsAffected)
// 根据Id删除resultDb= gplus.DeleteById[Student](studentItem.ID)
log.Printf("error:%v\n", resultDb.Error)
log.Printf("RowsAffected:%v\n", resultDb.RowsAffected)
// 根据条件删除query, model=gplus.NewQuery[Student]()
query.Eq(&model.Name, "zhangsan")
resultDb= gplus.Delete[Student](query)
log.Printf("error:%v\n", resultDb.Error)
log.Printf("RowsAffected:%v\n", resultDb.RowsAffected)
}

使用

定义表结构

typeStudentstruct {
IDintNamestringAgeuint8EmailstringBirthday time.TimeCreatedAt time.TimeUpdatedAt time.Time
}

连接数据库

和gorm的连接数据库的方式是一样的,只是多了一行 gplus.Init(gormDb),通过它来初始化gorm-plus的连接。

vargormDb*gorm.DBfuncinit() {
dsn:="root:root-abcd-1234@tcp(127.0.0.1:3306)/test?charset=utf8mb4&parseTime=True&loc=Local"varerrerrorgormDb, err=gorm.Open(mysql.Open(dsn), &gorm.Config{
Logger: logger.Default.LogMode(logger.Info),
})
iferr!=nil {
log.Println(err)
}
gplus.Init(gormDb)
}

自动迁移

varstudentStudentgormDb.AutoMigrate(student)

基础增删改查

插入一条数据

studentItem:=Student{Name: "zhangsan", Age: 18, Email: "123@11.com", Birthday: time.Now()}
gplus.Insert(&studentItem)

插入多条数据

student1:=Student{Name: "zhangsan1", Age: 18, Email: "123@11.com", Birthday: time.Now()}
student2:=Student{Name: "zhangsan2", Age: 18, Email: "123@11.com", Birthday: time.Now()}
varstudents= []*Student{&student1, &student2}
gplus.InsertBatch[Student](students)

分批插入数据

student1:=Student{Name: "zhangsan1", Age: 18, Email: "123@11.com", Birthday: time.Now()}
student2:=Student{Name: "zhangsan2", Age: 18, Email: "123@11.com", Birthday: time.Now()}
student3:=Student{Name: "zhangsan3", Age: 18, Email: "123@11.com", Birthday: time.Now()}
student4:=Student{Name: "zhangsan4", Age: 18, Email: "123@11.com", Birthday: time.Now()}
varstudents= []*Student{&student1, &student2, &student3, &student4}
// 每次插入2条数据gplus.InsertBatchSize[Student](students, 2)

根据一个ID查询

student, resultDb:= gplus.SelectById[Student](2)
log.Printf("error:%v\n", resultDb.Error)
log.Printf("RowsAffected:%v\n", resultDb.RowsAffected)
log.Printf("student:%+v\n", student)

根据多个ID查询

varids= []int{2, 3}
students, resultDb:= gplus.SelectByIds[Student](ids)
log.Printf("error:%v\n", resultDb.Error)
log.Printf("RowsAffected:%v\n", resultDb.RowsAffected)
for_, student:=rangestudents {
log.Printf("student:%+v\n", student)
}

根据条件查询一条数据

query, model:=gplus.NewQuery[Student]()
query.Eq(&model.Name, "zhangsan")
student, resultDb:=gplus.SelectOne(query)
log.Printf("error:%v\n", resultDb.Error)
log.Printf("RowsAffected:%v\n", resultDb.RowsAffected)
log.Printf("student:%v\n", student)

根据条件查询多条数据

query, model:=gplus.NewQuery[Student]()
query.Eq(&model.Name, "zhangsan")
students, resultDb:=gplus.SelectList(query)
log.Printf("error:%v\n", resultDb.Error)
log.Printf("RowsAffected:%v\n", resultDb.RowsAffected)
for_, student:=rangestudents {
log.Printf("student:%v\n", student)
}

根据条件查询多条数据(泛型封装)

有时候我们可能需要额外使用其他类型的接收数据,gplus也支持这种方式,通过传入第二个泛型参数来实现。

typeStudentVostruct {
NamestringAgeint
}
query, model:=gplus.NewQuery[Student]()
query.Eq(&model.Name, "zhangsan")
students, resultDb:= gplus.SelectListModel[Student, StudentVo](query)
log.Printf("error:%v\n", resultDb.Error)
log.Printf("RowsAffected:%v\n", resultDb.RowsAffected)
for_, student:=rangestudents {
log.Printf("student:%v\n", student)
}

根据条件分页查询

query, model:=gplus.NewQuery[Student]()
page:=gplus.NewPage[Student](1, 5)
query.Eq(&model.Name, "zhangsan")
page, resultDb:=gplus.SelectPage(page, query)
log.Printf("error:%v\n", resultDb.Error)
log.Printf("RowsAffected:%v\n", resultDb.RowsAffected)
log.Printf("total:%v\n", page.Total)
log.Printf("current:%v\n", page.Current)
log.Printf("size:%v\n", page.Size)
for_, student:=rangepage.Records {
log.Printf("student:%v\n", student)
}

根据条件分页查询(泛型封装)

typeStudentVostruct {
NamestringAgeint
}
query, model:=gplus.NewQuery[Student]()
page:=gplus.NewPage[StudentVo](1, 5)
query.Eq(&model.Name, "zhangsan")
page, resultDb:=gplus.SelectPageModel[Student, StudentVo](page, query)
log.Printf("error:%v\n", resultDb.Error)
log.Printf("RowsAffected:%v\n", resultDb.RowsAffected)
log.Printf("total:%v\n", page.Total)
log.Printf("current:%v\n", page.Current)
log.Printf("size:%v\n", page.Size)
for_, student:=rangepage.Records {
log.Printf("student:%v\n", student)
}

根据ID更新

student:=Student{ID: 3, Name: "lisi"}
student.Name="lisi"resultDb:= gplus.UpdateById[Student](&student)
log.Printf("error:%v\n", resultDb.Error)
log.Printf("RowsAffected:%v\n", resultDb.RowsAffected)

根据条件更新

query, model:=gplus.NewQuery[Student]()
query.Eq(&model.Name, "zhangsan").Set(&model.Age, 30)
resultDb:= gplus.Update[Student](query)
log.Printf("error:%v\n", resultDb.Error)
log.Printf("RowsAffected:%v\n", resultDb.RowsAffected)

根据ID删除

resultDb:= gplus.DeleteById[Student](4)
log.Printf("error:%v\n", resultDb.Error)
log.Printf("RowsAffected:%v\n", resultDb.RowsAffected)

根据多个ID删除

varids= []int{5, 6}
resultDb:= gplus.DeleteByIds[Student](ids)
log.Printf("error:%v\n", resultDb.Error)
log.Printf("RowsAffected:%v\n", resultDb.RowsAffected)

根据条件删除

query, model:=gplus.NewQuery[Student]()
query.Eq(&model.Name, "lisi")
resultDb:=gplus.Delete(query)
log.Printf("error:%v\n", resultDb.Error)
log.Printf("RowsAffected:%v\n", resultDb.RowsAffected)

高级查询

条件构造器

gorm-plus 提供了强大的条件构造器,通过构造器能够组合不同的查询条件。

方法名操作
Eq等于
Ne不等于
Gt大于
Ge大于等于
Lt小于
Le小于等于
LikeLIKE '%值%'
NotLikeNOT LIKE '%值%'
LikeLeftLIKE '%值'
LikeRightLIKE '值%'
IsNull字段 IS NULL
IsNotNull字段 IS NOT NULL
In字段 IN (值1,值2)
NotIn字段 NOT IN (值1,值2)
Between字段 BETWEEN 值1 ADN 值2
NotBetween字段 NOT BETWEEN 值1 ADN 值2

指针字段查询

通过NewQuery函数返回的第二个参数model,我们可以使用指针的方式来指定要使用的字段,无需再担心字段名写错。

query, model:=gplus.NewQuery[Student]()
query.Eq(&model.Name, "zhangsan1")
studentResult, resultDb:=gplus.SelectOne(query)
log.Printf("error:%v\n", resultDb.Error)
log.Printf("RowsAffected:%v\n", resultDb.RowsAffected)
log.Printf("studentResult:%+v\n", studentResult)

Query泛型简化

如果不希望每次创建Query对象的时候携带上泛型,我们可以提供一个全局的泛型Dao。

vardao gplus.Dao[Student]
funcmain() {
query, model:=dao.NewQuery()
query.Eq(&model.Name, "zhangsan")
list, resultDb:=gplus.SelectList(query)
fmt.Println(resultDb.RowsAffected)
for_, v:=rangelist {
marshal, _:=json.Marshal(v)
fmt.Println(string(marshal))
}
}

我们也可以把gplus.Dao组合到我们自己定义的Dao对象中

typeStudentDaostruct {
gplus.Dao[Student]
}
varstudentDaoStudentDaofuncmain() {
query, model:=studentDao.NewQuery()
query.Eq(&model.Name, "zhangsan")
list, resultDb:=gplus.SelectList(query)
fmt.Println(resultDb.RowsAffected)
for_, v:=rangelist {
marshal, _:=json.Marshal(v)
fmt.Println(string(marshal))
}
}

查询指定字段

通过Select来设置待查询的字段

query, model:=gplus.NewQuery[Student]()
query.Eq(&model.Name, "zhangsan1").Select(&model.Name)
studentResult, resultDb:=gplus.SelectOne(query)
log.Printf("error:%v\n", resultDb.Error)
log.Printf("RowsAffected:%v\n", resultDb.RowsAffected)
log.Printf("studentResult:%+v\n", studentResult)

排序

query, model:=gplus.NewQuery[Student]()
query.Eq(&model.Name, "zhangsan1").OrderByAsc(&model.Age)
students, resultDb:=gplus.SelectList(query)
log.Printf("error:%+v", resultDb.Error)
fmt.Println("RowsAffected:", resultDb.RowsAffected)
for_, student:=rangestudents {
log.Printf("student:%+v", student)
}

事务(未发版)

// 开启事务tx:=gplus.Begin()
// 使用defer,实现遇到错误时回滚defertx.Rollback()
// 新增,传入txstudent:=Student{Name: "zhangsan", Age: 18, Email: "123@11.com", Birthday: time.Now()}
result:=gplus.Insert(&student, tx)
...// 更新,传入txquery, model:=gplus.NewQuery[Student]()
query.Eq(&model.Name, "zhangsan").Set(&model.Age, 30)
resultDb:=gplus.Update[Student](query, tx)
...// 查询,如果需要在事务中查询,则也需要传入txresultStudent, db:=gplus.SelectById[Student](student.ID, tx)
...// 提交事务,否则数据库数据不更改tx.Commit()

About

Gorm-plus是基于Gorm的增强版,类似Mybatis-plus语法。Gorm-plus is based on an enhanced version of Gorm, similar to Mybatis-plus syntax.

Resources

Code of conduct

Stars

0 stars

Watchers

0 watching

Forks

Releases

Packages

Used by

Contributors

Languages