我想使用GORM在一个表("Mangas")中创建一个新的条目,该条目有一个指向另一个表("WebSites")的FK,但不幸的是,我在创建变量后无法保存数据,即使我在表中有一个我想要保存的条目.

为了澄清,我想有一个1:M的网站之间的关系-芒果和芒果-在MySQL数据库的章节.

//in package modules
type Website struct {
    gorm.Model
    Name             string
    Url              string
    MangaSearchQuery string
    Mangas           []Manga
}
type Manga struct {
    gorm.Model
    Name      string
    Url       string
    ImgUrl    string
    Chapters  []Chapter
    WebsiteID uint
    Website   Website `gorm:"constraint:OnUpdate:CASCADE,OnDelete:SET NULL;"`
}
type Chapter struct {
    gorm.Model
    Url     string
    WasRead bool
    MangaID uint
    Manga   Manga `gorm:"constraint:OnUpdate:CASCADE,OnDelete:SET NULL;"`
}

//in main
    db := modules.GetDatabaseInstance()

    manga := modules.Manga{
        Model:   gorm.Model{},
        Name:    "Test",
        Url:     "none",
        ImgUrl:  "example.com",
        //WebsiteID: 1,
        Website: modules.Website{Url: "test1"},
    }
    db.Create(manga)

我try 了多种答案,但都没有奏效.我认为它们可能适用于其他版本,因为每种方法都有很大的差异.有些要求我在运行db.Create之前向父表/接口添加一个子元素数组,另一些需要向接口添加ID或整行引用,但每次我都收到相同的错误:panic: reflect.Value.Addr of unaddressable value

我使用的是GO 1.21.0. 我不知道我的方法是不是一开始就错了,还是我漏掉了其他东西.

此外,我应该如何改进代码的建议是受欢迎的.?

推荐答案

要使用GORM使用指向"WebSites"表的外键在"Mangas"表中创建新条目,可以执行以下步骤:

  1. 更新您的模型以包括外键关系:
type Website struct {
    gorm.Model
    Name             string
    Url              string
    MangaSearchQuery string
    Mangas           []Manga
}

type Manga struct {
    gorm.Model
    Name      string
    Url       string
    ImgUrl    string
    Chapters  []Chapter
    WebsiteID uint
    Website   Website `gorm:"constraint:OnUpdate:CASCADE,OnDelete:SET NULL;"`
}

type Chapter struct {
    gorm.Model
    Url     string
    WasRead bool
    MangaID uint
    Manga   Manga `gorm:"constraint:OnUpdate:CASCADE,OnDelete:SET NULL;"`
}
  1. 通过将相关网站分配给漫画来创建条目:
db := modules.GetDatabaseInstance()

website := modules.Website{Url: "test1"}
db.Create(&website)

manga := modules.Manga{
    Name:    "Test",
    Url:     "none",
    ImgUrl:  "example.com",
    Website: website,
}

db.Create(&manga)
  1. 通过拨打db.Create并参考漫画对象来保存漫画.

通过将创建的网站分配给漫画中的Website字段,戈姆将自动创建关联,外键将保存在数据库中.

请注意,您需要将漫画和网站对象(&manga,&website)的地址传递给db.Create以保存数据.

为了进一步改进代码,您可以考虑使用事务和错误处理.下面是一个更新后的例子:

db := modules.GetDatabaseInstance()

website := modules.Website{Url: "test1"}
if err := db.Create(&website).Error; err != nil {
    // Handle the error
    fmt.Println("Error creating website:", err)
    return
}

manga := modules.Manga{
    Name:    "Test",
    Url:     "none",
    ImgUrl:  "example.com",
    Website: website,
}

tx := db.Begin()
if err := tx.Create(&manga).Error; err != nil {
    // Rollback the transaction if there's an error
    tx.Rollback()
    fmt.Println("Error creating manga:", err)
    return
}

// Commit the transaction if everything is successful
tx.Commit()

通过使用事务,您可以确保更改是原子的,并且可以处理数据库操作期间发生的任何错误.请记住导入必要的包(fmtgorm).

Go相关问答推荐

理解Golang并发:缓冲通道的意外行为

Websocket服务器实现与x/net库trowing 403

如何用Golang解码这个嵌套的json?

如何使用gopher-lua定义一个Lua函数,该函数有一个预定义的表作为param,Lua脚本可以在其中访问该函数中的表?

golang regex基于关键字拆分字符串

Cypher 查找(多个)最低 node

Prometheus 摘要分位数错误

为什么 Go 对于长度为 100k 的切片使用的内存比长度为 100k 的数组要少?

如何在 Go msgraph-sdk-go 中转发消息并包括抄送和/或密送收件人?

Exchange Web 服务 - 使用 soap xml 请求查找所有未读邮件

golang:解组动态 YAML 注释

具有嵌套重复的正则表达式

如何处理 Go 的 firebase admin sdk 错误?

仅在工作日运行 cron

为什么 reflect.TypeOf(new(Encoder)).Elem() != reflect.TypeOf(interfaceVariable)?

在删除级联时无法在 Gorm 中按预期工作

Go Fyne 禁用 HSplit 调整大小?

从 Go struct 中提取标签作为 reflect.Value

如何访问 Go 模板中数组的第一个索引的值

更改单个像素的 colored颜色 - Golang 图像