第七色在线视频,2021少妇久久久久久久久久,亚洲欧洲精品成人久久av18,亚洲国产精品特色大片观看完整版,孙宇晨将参加特朗普的晚宴

為了賬號安全,請及時綁定郵箱和手機立即綁定
已解決430363個問題,去搜搜看,總會有你想問的

gorm 預加載不適用于對象集合嗎?

gorm 預加載不適用于對象集合嗎?

Go
慕妹3242003 2022-05-23 16:50:29
我需要從 db where 獲取所有模塊status != Complete。我的模塊表與節(jié)表具有多對多映射,節(jié)表與字段表具有多對多映射。我正在嘗試使用下面的語句獲取單個 DB 查詢中的所有模塊。dbConnection.Set("gorm:auto_preload", true).Where("status != ?", enum.Completed).Find(&modules)但它不返回部分和字段。如果我使用下面的語句,那么它會返回嵌套模型。dbConnection.Set("gorm:auto_preload", true).Where("status != ?", enum.Completed).First(&modules)這是否意味著它僅適用于單個記錄而不適用于集合?
查看完整描述

2 回答

?
HUWWW

TA貢獻1874條經驗 獲得超12個贊

使用dbConnection.Set("gorm:auto_preload", true),您只能加載子關系,但如果您還想加載子的子關系,則必須使用嵌套預加載。像

db.Preload("Sections").Preload("Sections.Fields").Find(&modules)


查看完整回答
反對 回復 2022-05-23
?
守著星空守著你

TA貢獻1799條經驗 獲得超8個贊

我根據(jù)你的描述寫了一個示例代碼,你可以在底部找到完整的代碼。讓我們來看看不同的選擇:


// Use auto_preload and .First

db.Set("gorm:auto_preload", true).Where("name = ?", "m0").First(&modules)


Output:

[{ID:1 Name:m0 Status:0 Sections:[{ID:2 Name:s1 Fields:[]}]}]

因此,.First您可以得到部分,但不能得到Sections.Fields


// Use auto_preload and .Find

db.Set("gorm:auto_preload", true).Find(&modules)


Output:

[{ID:1 Name:m0 Status:0 Sections:[{ID:2 Name:s1 Fields:[]}]} {ID:2 Name:m1 Status:0 Sections:[{ID:1 Name:s0 Fields:[]}]}]

與.Find您獲得相同的行為.First


// Use .Preload

db.Preload("Sections").Preload("Sections.Fields").Find(&modules)


Output:

[{ID:1 Name:m0 Status:0 Sections:[{ID:2 Name:s1 Fields:[{ID:1 Name:f0} {ID:2 Name:f1}]}]} {ID:2 Name:m1 Status:0 Sections:[{ID:1 Name:s0 Fields:[{ID:1 Name:f0} {ID:3 Name:f2}]}]}]

通過顯式預加載,您可以同時加載Sections和Sections.Fields。僅使用auto_preload預加載直接字段,而不是更深的字段。IMO 使用顯式預加載通常是一種更好的做法。


完整代碼:


package main


import (

    "fmt"

    "github.com/jinzhu/gorm"

    _ "github.com/jinzhu/gorm/dialects/sqlite"

    "log"

)


type Module struct {

    ID       int `gorm:"primary_key"`

    Name     string

    Status   int

    Sections []Section `gorm:"many2many:module_sections;"`

}


type Section struct {

    ID     int `gorm:"primary_key"`

    Name   string

    Fields []Field `gorm:"many2many:section_fields;"`

}


type Field struct {

    ID   int `gorm:"primary_key"`

    Name string

}


func preloadingSample() error {

    db, err := gorm.Open("sqlite3", "test.db")

    if err != nil {

        return fmt.Errorf("open DB failed: %w", err)

    }

    defer db.Close()


    err = db.AutoMigrate(

        &Module{},

        &Section{},

        &Field{},

    ).Error

    if err != nil {

        return fmt.Errorf("migration failed: %w", err)

    }


    // Delete everything in DB

    db.Delete(&Module{})

    db.Delete(&Section{})

    db.Delete(&Field{})


    // Put some sample data in DB

    sampleFields := []Field{

        {Name: "f0"},

        {Name: "f1"},

        {Name: "f2"},

        {Name: "f3"},

    }

    for idx := range sampleFields {

        err = db.Create(&sampleFields[idx]).Error

        if err != nil {

            return fmt.Errorf("failed to create: %w", err)

        }

    }


    sampleSections := []Section{

        {Name: "s0", Fields: []Field{sampleFields[0], sampleFields[2]}},

        {Name: "s1", Fields: []Field{sampleFields[0], sampleFields[1]}},

    }

    for idx := range sampleSections {

        err = db.Create(&sampleSections[idx]).Error

        if err != nil {

            return fmt.Errorf("failed to create: %w", err)

        }

    }


    sampleModules := []Module{

        {Name: "m0", Sections: []Section{sampleSections[1]}},

        {Name: "m1", Sections: []Section{sampleSections[0]}},

    }

    for idx := range sampleModules {

        err = db.Create(&sampleModules[idx]).Error

        if err != nil {

            return fmt.Errorf("failed to create: %w", err)

        }

    }


    var modules []Module


    // Load just one module with auto_preload

    err = db.Set("gorm:auto_preload", true).Where("name = ?", "m0").First(&modules).Error

    if err != nil {

        return fmt.Errorf("auto_preload first: %w", err)

    }

    fmt.Printf("%+v\n", modules)


    // Load all modules with auto_preload

    err = db.Set("gorm:auto_preload", true).Find(&modules).Error

    if err != nil {

        return fmt.Errorf("auto_preload find: %w", err)

    }

    fmt.Printf("%+v\n", modules)


    // Explicitly load

    err = db.Preload("Sections").Preload("Sections.Fields").Find(&modules).Error

    if err != nil {

        return fmt.Errorf("preload find: %w", err)

    }

    fmt.Printf("%+v\n", modules)


    return nil

}


func main() {

    err := preloadingSample()

    if err != nil {

        log.Fatal(err)

    }

}



查看完整回答
反對 回復 2022-05-23
  • 2 回答
  • 0 關注
  • 184 瀏覽
慕課專欄
更多

添加回答

舉報

0/150
提交
取消
微信客服

購課補貼
聯(lián)系客服咨詢優(yōu)惠詳情

幫助反饋 APP下載

慕課網(wǎng)APP
您的移動學習伙伴

公眾號

掃描二維碼
關注慕課網(wǎng)微信公眾號