当前位置: 首页 > news >正文

go语言Gin框架的学习路线(八)

目录

GORM Model定义

使用 Model 结构体的自定义数据模型

理解并记忆 GORM 的 Model 结构体可以通过以下几个步骤和技巧:

1. 理解基本概念

2. 熟悉基本字段

3. 记忆技巧

4. 使用场景

结构体标记

支持的结构体标记(Struct tags)

关联相关标记(tags)

GROM(默认行为)主键、表名的约定

主键(Primary Key)

表名(Table Name)

也可以通过Table()指定表名:

GORM还支持更改默认表名称规则:

示例应用场景:

时间戳跟踪

CreatedAt

UpdatedAt

DeletedAt


GORM Model定义(基于七米老师)

GORM 的 Model 是一个内嵌的结构体,它提供了一组通用的模型字段和方法,使得在定义你的数据模型时更加方便和一致。

GORM 的 Model 结构体通常定义如下:

type Model struct {ID        uintCreatedAt time.Time `gorm:"column:create_at"`UpdatedAt time.Time `gorm:"column:update_at"`DeletedAt gorm.DeletedAt `gorm:"column:deleted_at"`
}
  • ID 是一个自增的主键。
  • CreatedAt 和 UpdatedAt 是记录创建和更新时间的时间戳字段。
  • DeletedAt 是一个用于软删除的字段(如果使用软删除功能)。

使用 Model 结构体的自定义数据模型

以下是如何在自定义数据模型中使用 Model 结构体(你可以将它嵌入到你自己的模型中)的示例:

package mainimport ("gorm.io/driver/sqlite""gorm.io/gorm""log""time"
)// Model 是 GORM 的基础模型,内嵌在其他模型中
type Model struct {ID        uintCreatedAt time.Time `gorm:"column:create_at"`UpdatedAt time.Time `gorm:"column:update_at"`DeletedAt gorm.DeletedAt `gorm:"column:deleted_at"`
}// User 定义了一个用户模型,内嵌了 GORM 的 Model 结构体
type User struct {Model     // 内嵌 Model 以获得通用字段Name      stringAge       intEmail     string
}func main() {// 连接到 SQLite 数据库,实际使用中可能连接到 MySQL、PostgreSQL 等dsn := "file:db.sqlite?mode=memory&cache=shared&_fk=1"db, err := gorm.Open(sqlite.Open(dsn), &gorm.Config{})if err != nil {log.Fatal(err)}// 自动迁移数据库模式db.AutoMigrate(&User{})// 创建新用户user := User{Name: "Alice", Age: 30, Email: "alice@example.com"}db.Create(&user)// 查询用户var users []Userdb.Find(&users)log.Println(users)// 更新用户信息db.Model(&User{Name: "Alice"}).Updates(User{Age: 31})// 删除用户db.Delete(&User{Name: "Alice"}, &User{})
}

在这个示例中:

  • Model 结构体定义了一组通用字段,如 IDCreatedAtUpdatedAt 和 DeletedAt
  • User 结构体内嵌了 Model,从而自动获得了这些通用字段。
  • 使用 AutoMigrate 方法自动创建数据库表,确保表结构与 User 结构体一致。
  • 使用 Create 方法添加新用户。
  • 使用 Find 方法查询用户。
  • 使用 Model 方法和 Updates 来更新用户信息。
  • 使用 Delete 方法删除用户。

这样,你就可以在你的应用程序中方便地使用 GORM 的 Model 结构体来简化数据库操作。

理解并记忆 GORM 的 Model 结构体可以通过以下几个步骤和技巧:

1. 理解基本概念

  • ORM: 对象关系映射,允许你使用面向对象的方式来操作数据库。
  • Model: GORM 中的 Model 是一个内嵌结构体,提供了数据库操作的通用字段和行为。

2. 熟悉基本字段

  • ID: 主键,通常用于唯一标识数据库记录。
  • CreatedAt: 创建时间,记录记录被创建的时间。
  • UpdatedAt: 更新时间,记录记录最后被更新的时间。
  • DeletedAt: 软删除时间,用于实现软删除功能。

3. 记忆技巧

  • 首字母法: 记住字段的首字母,如 I (ID), C (CreatedAt), U (UpdatedAt), D (DeletedAt).
  • 关联记忆: 将字段与实际的数据库操作关联起来,比如 CreatedAt 与记录的创建时间关联。

4. 使用场景

  • 定义模型: 在定义你的数据模型时,通常会内嵌 Model 结构体。
  • 自动字段: 内嵌 Model 后,你的模型会自动获得 IDCreatedAtUpdatedAt 等字段

结构体标记

使用结构体声明模型时,标记(tags)是可选项。gorm支持以下标记:

支持的结构体标记(Struct tags)
结构体标记(Tag)描述
Column指定列名
Type指定列数据类型
Size指定列大小, 默认值255
PRIMARY_KEY将列指定为主键
UNIQUE将列指定为唯一
DEFAULT指定列默认值
PRECISION指定列精度
NOT NULL将列指定为非 NULL
AUTO_INCREMENT指定列是否为自增类型
INDEX创建具有或不带名称的索引, 如果多个索引同名则创建复合索引
UNIQUE_INDEX和 INDEX 类似,只不过创建的是唯一索引
EMBEDDED将结构设置为嵌入
EMBEDDED_PREFIX设置嵌入结构的前缀
-忽略此字段
关联相关标记(tags)
结构体标记(Tag)描述
MANY2MANY指定连接表
FOREIGNKEY设置外键
ASSOCIATION_FOREIGNKEY设置关联外键
POLYMORPHIC指定多态类型
POLYMORPHIC_VALUE指定多态值
JOINTABLE_FOREIGNKEY指定连接表的外键
ASSOCIATION_JOINTABLE_FOREIGNKEY指定连接表的关联外键
SAVE_ASSOCIATIONS是否自动完成 save 的相关操作
ASSOCIATION_AUTOUPDATE是否自动完成 update 的相关操作
ASSOCIATION_AUTOCREATE是否自动完成 create 的相关操作
ASSOCIATION_SAVE_REFERENCE是否自动完成引用的 save 的相关操作
PRELOAD是否自动完成预加载的相关操作

GROM(默认行为)主键、表名的约定

主键(Primary Key)

GORM 默认会使用名为ID的字段作为表的主键。

type User struct {ID   string // 名为`ID`的字段会默认作为表的主键Name string
}// 使用`AnimalID`作为主键
type Animal struct {AnimalID int64 `gorm:"primary_key"`Name     stringAge      int64
}

 

表名(Table Name)

表名默认就是结构体名称的复数,例如:

package mainimport ("gorm.io/driver/sqlite""gorm.io/gorm""log"
)// User 定义了一个用户模型
type User struct {gorm.ModelName  stringAge   intEmail string
}func main() {// 连接到 SQLite 数据库dsn := "file:db.sqlite?mode=memory&cache=shared&_fk=1"db, err := gorm.Open(sqlite.Open(dsn), &gorm.Config{})if err != nil {log.Fatal(err)}// 自动迁移数据库模式db.AutoMigrate(&User{})// 创建新用户user := User{Name: "Alice", Age: 30, Email: "alice@example.com"}db.Create(&user)// 查询用户var users []Userdb.Find(&users)log.Println(users)
}

在这个例子中:

  • User 结构体定义了一个用户模型,内嵌了 gorm.Model 以获得通用字段。
  • 表名默认为 "users",因为 GORM 将 "User" 自动转换为复数形式。
  • 使用 AutoMigrate 方法自动创建数据库表,确保表结构与 User 结构体一致。
  • 使用 Create 方法添加新用户。
  • 使用 Find 方法查询用户。

这样,你就可以看到 GORM 如何自动处理表名的生成。

禁用默认表名的复数形式,如果置为 true,则 `User` 的默认表名是 `user`

db.SingularTable(true)
也可以通过Table()指定表名:
// 使用User结构体创建名为`deleted_users`的表
db.Table("deleted_users").CreateTable(&User{})var deleted_users []User
db.Table("deleted_users").Find(&deleted_users)SELECT * FROM deleted_users;db.Table("deleted_users").Where("name = ?", "jinzhu").Delete()DELETE FROM deleted_users WHERE name = 'jinzhu';

这段代码展示了 GORM 提供的灵活性,允许你通过 Table 方法指定表名,而不是依赖 GORM 自动推断的表名。这对于需要使用特定表名或已经存在的表名与 GORM 模型名称不匹配的情况非常有用。 

GORM还支持更改默认表名称规则:
gorm.DefaultTableNameHandler = func (db *gorm.DB, defaultTableName string) string  {return "prefix_" + defaultTableName;
}

这段代码是 GORM 的一个配置示例,用于自定义表名的生成规则。GORM 允许你通过设置 gorm.DefaultTableNameHandler 来改变表名的默认生成逻辑。下面是对代码的详细解释:

  • gorm.DefaultTableNameHandler: 这是一个全局变量,它是一个函数,用于处理和生成表名。

  • 函数签名 func(db *gorm.DB, defaultTableName string) string: 这个函数接收两个参数,第一个是 *gorm.DB 类型的 db,表示当前的数据库连接实例;第二个是 defaultTableName 字符串,表示 GORM 根据模型名称自动生成的默认表名。函数返回一个字符串,即自定义后的表名。

  • return "prefix_" + defaultTableName: 这个函数的实现非常简单,它将为所有自动生成的表名添加前缀 "prefix_"。例如,如果模型名称是 User,GORM 默认会生成表名为 "users",使用这个函数后,表名将变为 "prefix_users"

示例应用场景:

假设你有一个数据库,所有表都遵循特定的命名规范,比如都以 "app_" 作为前缀。你可以设置 gorm.DefaultTableNameHandler 来确保所有模型都遵循这个规范:

时间戳跟踪

CreatedAt

如果模型有 CreatedAt字段,该字段的值将会是初次创建记录的时间。

db.Create(&user) // `CreatedAt`将会是当前时间// 可以使用`Update`方法来改变`CreateAt`的值
db.Model(&user).Update("CreatedAt", time.Now())
UpdatedAt

如果模型有UpdatedAt字段,该字段的值将会是每次更新记录的时间。

db.Save(&user) // `UpdatedAt`将会是当前时间db.Model(&user).Update("name", "jinzhu") // `UpdatedAt`将会是当前时间
DeletedAt

如果模型有DeletedAt字段,调用Delete删除该记录时,将会设置DeletedAt字段为当前时间,而不是直接将记录从数据库中删除。

 

期末放假自学Gin框架,希望我们可以一起学习!

相关文章:

  • 北京网站建设多少钱?
  • 辽宁网页制作哪家好_网站建设
  • 高端品牌网站建设_汉中网站制作
  • 基于3D开发引擎HOOPS平台的大型三维PLM系统的设计、开发与应用
  • Linux之基础IO(上)
  • TeraTerm 使用技巧
  • 什么是单例模式,有哪些应用?
  • 模板、STL 简介(深度剖析)
  • VisualRules-Web案例展示(一)
  • mysql、oracle、db2数据库连接参数
  • SpringSecurity通用权限管理系统
  • 关于合芯新通RTK配置的方法记录7.23
  • k8s部署rabbitmq集群
  • Json结构解析比较
  • 69、ncnn学习onnx2ncnn不支持带三维算子相乘gemm/repeat转换方法学习
  • CH04_依赖项属性
  • day02 mybatis
  • 微信小程序数组绑定使用案例(二)
  • Android优雅地处理按钮重复点击
  • C++类中的特殊成员函数
  • JavaScript创建对象的四种方式
  • Mybatis初体验
  • node学习系列之简单文件上传
  • ubuntu 下nginx安装 并支持https协议
  • 从零开始的无人驾驶 1
  • 翻译--Thinking in React
  • 复杂数据处理
  • 关于springcloud Gateway中的限流
  • 老板让我十分钟上手nx-admin
  • 聊聊flink的BlobWriter
  • 小程序上传图片到七牛云(支持多张上传,预览,删除)
  • HanLP分词命名实体提取详解
  • ​【经验分享】微机原理、指令判断、判断指令是否正确判断指令是否正确​
  • ​第20课 在Android Native开发中加入新的C++类
  • #100天计划# 2013年9月29日
  • (多级缓存)缓存同步
  • (附源码)ssm高校志愿者服务系统 毕业设计 011648
  • (附源码)计算机毕业设计ssm电影分享网站
  • (十七)Flink 容错机制
  • (一)使用IDEA创建Maven项目和Maven使用入门(配图详解)
  • (中等) HDU 4370 0 or 1,建模+Dijkstra。
  • (终章)[图像识别]13.OpenCV案例 自定义训练集分类器物体检测
  • .NET 8 编写 LiteDB vs SQLite 数据库 CRUD 接口性能测试(准备篇)
  • .NET Core IdentityServer4实战-开篇介绍与规划
  • .Net 高效开发之不可错过的实用工具
  • .NET 通过系统影子账户实现权限维持
  • .Net6支持的操作系统版本(.net8已来,你还在用.netframework4.5吗)
  • .net之微信企业号开发(一) 所使用的环境与工具以及准备工作
  • .net中应用SQL缓存(实例使用)
  • @font-face 用字体画图标
  • [ 渗透测试面试篇 ] 渗透测试面试题大集合(详解)(十)RCE (远程代码/命令执行漏洞)相关面试题
  • [1525]字符统计2 (哈希)SDUT
  • [240812] X-CMD 发布 v0.4.5:更新 gtb、cd、chat、hashdir 模块功能
  • [Android开源]EasySharedPreferences:优雅的进行SharedPreferences数据存储操作
  • [Avalon] Avalon中的Conditional Formatting.
  • [BT]BUUCTF刷题第4天(3.22)
  • [BUUCTF NewStarCTF 2023 公开赛道] week4 crypto/pwn
  • [C#]DataTable常用操作总结【转】