gorm高级使用

张开发
2026/4/3 23:13:24 15 分钟阅读
gorm高级使用
一、从数据库中随机返回一条数据1、方式一直接写原生sqSELECT*FROMuserORDERBYRAND()LIMIT12、方式二使用clause.OrderBy来写函数查询varuserEntity model.UserEntity err:dao.UserEntity.UnderlyingDB().WithContext(ctx).Clauses(clause.OrderBy{Expression:clause.Expr{SQL:RAND(),WithoutParentheses:true},}).Take(userEntity).Error3、使用随机函数varmaxIDuintdao.UserEntity.WithContext(ctx).Select(dao.UserEntity.ID.Max()).Scan(maxID)// 生成随机ID假设ID从1开始连续ifmaxID0{randID:rand.Intn(int(maxID))1userEntity,err:dao.UserEntity.WithContext(ctx).Where(dao.UserEntity.ID.Gte(int64(randID))).Take()iferrnil{utils.Success(ctx,userEntity)return}}二、 锁的使用官网文档地址,链接地址关于锁的使用必须是在事务中使用否则无效注意:如果没有使用索引的话会直接升级为表锁1、关于mysql中表里面锁的几种行锁锁定一行数据SELECT * FROM user WHERE id 1 FOR UPDATE;共享锁可读不可写SELECT * FROM user WHERE id 1 LOCK IN SHARE MODE;2、行锁的具体的使用u:dao.UsersEntity user,err:u.WithContext(ctx).Clauses(clause.Locking{Strength:UPDATE}).Where(u.ID.Eq(1)).First()// SELECT * FROM user WHERE id 1 FOR UPDATE;3、共享锁的使用u:dao.UsersEntity user,err:u.WithContext(ctx).Clauses(clause.Locking{Strength:SHARE}).Where(u.ID.Eq(1)).First()// SELECT * FROM user WHERE id 1 LOCK IN SHARE MODE;4、常见使用(扣减库存的时候)err:db.Transaction(func(tx*gorm.DB)error{p:query.Product.WithContext(ctx).UseDB(tx)product,err:p.Clauses(clause.Locking{Strength:UPDATE}).Where(p.ID.Eq(productId)).First()iferr!nil{returnerr}ifproduct.Stock1{returnerrors.New(库存不足)}_,errp.Where(p.ID.Eq(productId)).Update(p.Stock,product.Stock-1)returnerr})三、其他高级使用1、Upsert操作,指定字段来创建或更新字段使用场景防止重复数据dao.UserEntity.WithContext(ctx).Clauses(clause.OnConflict{Columns:[]clause.Column{{Name:email}},DoNothing:true,// 表示什么都不做}).Create(model.UserEntity{Email:1qq.com,Password:123456,PassSalt:123456,})2、存在的时候就更新指定的字段dao.UserEntity.WithContext(ctx).Clauses(clause.OnConflict{Columns:[]clause.Column{{Name:email}},DoUpdates:clause.AssignmentColumns([]string{updated_at}),// 更新指定字段}).Create(model.UserEntity{Email:1qq.com,Password:123456,PassSalt:123456,})3、存在的时候更新全部的字段dao.UserEntity.WithContext(ctx).Clauses(clause.OnConflict{Columns:[]clause.Column{{Name:email}},UpdateAll:true,// 表示更新全部的字段}).Create(model.UserEntity{Email:1qq.com,Password:123456,PassSalt:123456,})4、备注说明其中根据指定的字段来创建或更新这个字段必须是唯一索引如果是多个字段多个字段一起是唯一索引四、在gorm-gen中使用普通的sql写法这种情况是针对于gorm-gen不能满足需求的时候才使用1、直接使用聚合函数varuserListmake([]model.UsersEntity,0)err:dao.UsersEntity.WithContext(context.Background()).Select(dao.UsersEntity.ID,field.NewUnsafeFieldRaw(COALESCE(NULLIF(TRIM(name), ), 默认名称) AS name),field.NewUnsafeFieldRaw(COALESCE(name_id, 1) AS name_id),).Scan(userList)

更多文章