这是我参与「第三届青训营 -后端场」笔记创作活动的第3篇笔记。 本文章参考gorm官方文档:gorm.io/docs/
has many关联就是创建和另一个模型的一对多关系, 不像has one,所有者可以拥有 0 个或多个模型实例。 gorm官方文档例子:
// 用户有多张信用卡,UserID 是外键
type User struct {
gorm.Model
CreditCards []CreditCard
}
type CreditCard struct {
gorm.Model
Number string
UserID uint
}
在本次抖音项目开发中,User的Follows和Followers字段也是这种类型,属于has many 自引用
// 每个用户有多个粉丝,每个用户有多个关注的用户
// 通过 'gorm:"foreignkey:UserId"'指定外键
type User struct {
UserId int64 `json:"id,omitempty" gorm:"primaryKey"`
Name string `json:"name,omitempty" gorm:"unique"`
FollowCount int64 `json:"follow_count,omitempty"`
FollowerCount int64 `json:"follower_count,omitempty"`
IsFollow bool `json:"is_follow,omitempty"`
PassWord string `json:"pass_word,omitempty"`
Follows []User `json:"follows,omitempty" gorm:"foreignkey:UserId"`
Followers []User `json:"followers,omitempty" gorm:"foreignkey:UserId"`
FavoriteVideos []Video `json:"favorite_videos,omitempty" gorm:"many2many:user_videos"`
}
many to many为两个模型增加了一个中间表。 gorm官方文档例子:
// 用户有多张信用卡,UserID 是外键
type User struct {
gorm.Model
CreditCards []CreditCard
}
type CreditCard struct {
gorm.Model
Number string
UserID uint
}
在本次抖音项目开发中,为了方便取出用户点赞过的视频,添加了FavoriteVideos字段,属于many2many类型
// 每个用户有多个喜欢的video,每个video也被多个用户喜欢
// 通过 'gorm:"many2many:user_videos'指定中间表
type User struct {
UserId int64 `json:"id,omitempty" gorm:"primaryKey"`
Name string `json:"name,omitempty" gorm:"unique"`
FollowCount int64 `json:"follow_count,omitempty"`
FollowerCount int64 `json:"follower_count,omitempty"`
IsFollow bool `json:"is_follow,omitempty"`
PassWord string `json:"pass_word,omitempty"`
Follows []User `json:"follows,omitempty" gorm:"foreignkey:UserId"`
Followers []User `json:"followers,omitempty" gorm:"foreignkey:UserId"`
FavoriteVideos []Video `json:"favorite_videos,omitempty" gorm:"many2many:user_videos"`
}
CURD操作: 通过Association() 根据实际情况使用 Delete() Append() Replace()等方法
本次项目开发中用到的部分CURD操作
func AddUserFavoriteVideos(user *User, video *Video) {
DB.Model(user).Association("FavoriteVideos").Append(video)
AddVideoFavoriteNum(video.VideoId, video.FavoriteCount)
}
func RemoveUserFavoriteVideos(user *User, video *Video) {
DB.Model(user).Association("FavoriteVideos").Delete(video)
RemoveVideoFavoriteNum(video.VideoId, video.FavoriteCount)
}