如何使用 gorm 获取双嵌套数据?

How to get double nested data with gorm?

我正在开发一个使用 go 和 gorm 管理报价的应用程序。用户创建报价,报价有多个标签,用户可以将报价添加到收藏夹。

我想获取用户已添加到收藏夹的名言列表。那时,我想获得附加在引号上的标签。

这是我的数据模型。

type Quote struct {
    ID            int       `gorm:"primary_key" json:"id"`
    CreatedAt     time.Time `json:"created_at"`
    UpdatedAt     time.Time `json:"updated_at"`
    Text          string    `json:"text"`
    Page          int       `json:"page"`
    Published     bool      `gorm:"default:false" json:"published"`
    Tags          []Tag     `gorm:"many2many:quotes_tags;" json:"tags"`
    User          User      `json:"user"`
    UserID        string    `json:"user_id"`
    FavoriteUsers []User    `gorm:"many2many:users_quotes;" json:"favorite_users"`
}

type User struct {
    ID              string    `json:"id"`
    CreatedAt       time.Time `json:"created_at"`
    UpdatedAt       time.Time `json:"updated_at"`
    Username        string    `json:"username"`
    Quotes          []Quote   `json:"quotes"`
    FavoriteQuotes  []Quote   `gorm:"many2many:users_quotes;" json:"favorite_quotes"`
}

type Tag struct {
    ID        int       `gorm:"primary_key" json:"id"`
    CreatedAt time.Time `json:"created_at"`
    Name      string    `json:"name"`
}

我尝试了以下方法并得到了最喜欢的报价,但标签为空。有没有办法用 gorm 做到这一点?提前谢谢你。

func (service *Service) GetUser(uid string) (models.User, error) {
    fmt.Println(uid)
    user := models.User{}
    if result := service.db.Preload(clause.Associations).First(&user, "id = ?", uid); result.Error != nil {
        return models.User{}, result.Error
    }
    return user, nil
}

func (service *Service) GetFavoriteQuotes(uid string) ([]models.Quote, error) {
    user, err := service.GetUser(uid)
    if err != nil {
        return []models.Quote{}, err
    }
    return user.FavoriteQuotes, nil
}

如果您查看 Preload All 文档,它说:

clause.Associations won’t preload nested associations, but you can use it with Nested Preloading

在你的情况下,这将是这样的:

if result := service.db.Preload("FavoriteQuotes.Tags").Preload(clause.Associations).First(&user, "id = ?", uid); result.Error != nil {
        return models.User{}, result.Error
    }