美文网首页
GORM many2many关系表的创建和查询

GORM many2many关系表的创建和查询

作者: _敏讷 | 来源:发表于2020-03-27 19:22 被阅读0次

最近在用golang搭建个人博客的后台,数据库选用了gorm + mySQL的组合,其中文章(articles)和标签(tags)两个表是多对多的关系,由于对数据库不是很熟悉,外加gorm的文档较为简略,在这里踩了很多的坑。现在在这篇文章中总结下实现的方法。

第一步:定义gorm表的struct

type Article struct {
    gorm.Model
    Title     string            `gorm:"not null"`
    Content   string    `gorm:"not null"`
    Tags      []Tag     `gorm:"many2many:tag_articles"`
}

type Tag struct {
    TagId       string      `gorm:"primary_key"`
    TagName   string        `gorm:"unique;not null"`
    Articles  []Article     `gorm:"many2many:tag_articles"`
}

第二步:连接数据库,创建表

func InitDB() *gorm.DB {
    //创建一个数据库的连接
    var err error
    db, err := gorm.Open("mysql","root:071918@tcp(127.0.0.1:3306)/blog?charset=utf8")
    if err != nil {
        panic(err)
    }

    // 调用该语句会自动生成联结表tag_articles
    db.AutoMigrate(&Article{}, &Tag{})
    return db
}

第三步:存数据

tag1 := Tag{ TagId: "001", TagName: "React" }
db.Save(&tag1)
article := Article{
    Title: "Redux进阶教程", 
        Content:   "正文内容",
        // 子项中的数据必须是保存过或者查找出的数据(即数据库已有的数据)
        Tags: []Tag {
        tag1,
    },
}

或者

tagIdList := ["001", "002"]
var tags []db.Tag
// 分别查询tagIdList,并将结果插入tags列表
for i := range tagIdList {
    tag := db.Tag{}
    DB.Where("tag_id = ?", tagIdList[i]).First(&tag)
    tags = append(tags, tag)
}

articleModel := db.Article{
    Title:  "这是标题",
    Content:  "这是正文",
    Tags:      tags,
}
// 保存
err := DB.Save(&articleModel)

在上述步骤中有需要注意的是,Tags对应的数组项必须事先存入数据库,或者事先查找过,否则仅会生成article的记录,不会生成tag_articles联结表的记录。

第四步:查询

因为不熟悉gorm的API,有一部分查询是使用基本的sql语句查询的,性能方面可能不太好,但是作为个人博客后端使用问题不大。

查询带标签(Tag)子项的文章(Article)列表

var articleList []Article
err := DB.Preload("Tags").Find(&articleList)
fmt.Println(articleList)

查询带文章数(Count)的标签(Tag)列表

// 定义所需的struct
type tagResult struct {
    Count int
    TagName string
    TagId   string
}
var tagList []tagResult
err := DB.Raw("SELECT COUNT(*) count, t.tag_name, t.tag_id " +
    // 下面这句使用笛卡尔积连接两个表,复杂度变成了m * n,性能较差
    "FROM tag_articles ta, tags t " +
    "WHERE t.tag_id=ta.tag_tag_id " +
    "GROUP BY ta.tag_tag_id ").Scan(&tagList)
fmt.Println(tagList)

根据标签(TagId)查询全部文章列表

// 定义所需的struct
type articleResult struct {
    Title     string
    ArticleId string
}
var articleList []articleResult
tagId := "001"
// 查询语句
err := DB.Raw("SELECT a.title, a.article_id "+
        // 下面这句使用笛卡尔积连接两个表,复杂度变成了m * n,性能较差
    "FROM tag_articles ta, articles a "+
    "WHERE a.article_id=ta.article_article_id "+
    "AND ta.tag_tag_id= ? ", tagId).Scan(&articleList)
fmt.Println(articleList)

相关文章

  • GORM many2many关系表的创建和查询

    最近在用golang搭建个人博客的后台,数据库选用了gorm + mySQL的组合,其中文章(articles)和...

  • gorm 如何执行新增和更新逻辑

    gorm本身不具备一个方法执行 创建和更新数据 需要进行判断 gorm查询分页

  • odoo中操作第三章表

    自定义第三章表的表名,自身关联many2many sql语句操作第三张表,增加数据 查询

  • gorm 建立many2many关系的坑

    使用gorm建立多对多关系时,发现没有成功,报错:Error 1075: Incorrect table defi...

  • Gorm for SQL Join 关联查询

    Gorm for SQL Join 关联查询 Belongs To: http://gorm.io/docs/be...

  • 以SQL为导向大幅优化Grails GORM性能

    之前曾经写过一篇文章,Grails GORM查询总结,介绍了Grails中GORM查询的几种方式。在结语中,我写道...

  • mysql查询、事物(四)

    知识要点: 单表查询 子查询 联表查询 事务 在进行查询之前,我们要先建好关系表,并往数据表中插入些数据。为查询操...

  • 关联关系查询(第一讲)

    关联查询 当查询内容涉及到具有关联关系的多个表时,就需要使用关联查询。根据表与表之间的关联关系的不同,关联查询分为...

  • 17/12/13创建和维护表

    17/12/13创建和维护表 创建表 运用子查询语句创建表 修改表 添加列 修改列 删除列 删除表 重命名表 把e...

  • mysql表关系

    mysql数据库 知识要点: 单表查询 子查询 联表查询 事务 在进行查询之前,我们要先建好关系表,并往数据表中插...

网友评论

      本文标题:GORM many2many关系表的创建和查询

      本文链接:https://www.haomeiwen.com/subject/jhhruhtx.html