簡體   English   中英

檢索父母和孩子 - 自引用實體 gorm

[英]Retrieving Parents and Children - Self Referencing Entity gorm

我有一個表,它有一個層次結構,一個有很多孩子的父母和一個有很多父母的孩子。

例如以下結構:

type User struct {
    gorm.Model
    Name       string
    SubUsers   []*User `gorm:"many2many:user_sub_users;constraint:OnDelete:CASCADE"`
    SuperUsers []*User `gorm:"many2many:user_sub_users.......` // no idea what to fill here

}

為了能夠檢索一個實體的超級用戶(父母),我需要添加什么配置?

所以,作為一個例子,想象我有以下

Table users
| ID | name   |
--------------=
| 1  | Alice  |
| 2  | Bob    |
| 3  | Joe    |
| 4  | Manuel |
---------------

Table users_sub_users
| ID | user_id  | sub_user_id |
-------------------------------
| 1  |   1      |    2        |
| 2  |   1      |    3        |
| 3  |   4      |    1        |
-------------------------------

因此,如果我檢索用戶 Alice,我想得到以下信息:

Alice ->
   SubUsers: [Bob, Joe]
   SuperUsers: [Manuel]

您可以使用joinForeignKeyjoinReferences指定表user_sub_users中的字段。

代替:

SubUsers   []*User `gorm:"many2many:user_sub_users"`

它會更明確:

SubUsers   []*User `gorm:"many2many:user_sub_users;joinForeignKey:sub_user_id;joinReferences:user_id;"`

對於SuperUsers ,只需交換字段:

SuperUsers []*User `gorm:"many2many:user_sub_users;joinForeignKey:user_id;joinReferences:sub_user_id;"`

最小的例子:

package main

import (
    "fmt"

    "github.com/glebarez/sqlite"
    "gorm.io/gorm"
)

type User struct {
    gorm.Model
    Name       string
    SubUsers   []*User `gorm:"many2many:user_sub_users;joinForeignKey:sub_user_id;joinReferences:user_id;"`
    SuperUsers []*User `gorm:"many2many:user_sub_users;joinForeignKey:user_id;joinReferences:sub_user_id;"`
}

func main() {
    db, err := gorm.Open(sqlite.Open("test.db"), &gorm.Config{})
    if err != nil {
        panic(err)
    }

    db.AutoMigrate(&User{})

    alice := &User{Name: "Alice"}
    db.Create(alice)
    bob := &User{Name: "Bob"}
    db.Create(bob)
    joe := &User{Name: "Joe"}
    db.Create(joe)
    manuel := &User{Name: "Manuel"}
    db.Create(manuel)

    err = db.Model(alice).Association("SubUsers").Append(bob, joe)
    if err != nil {
        panic(err)
    }
    err = db.Model(manuel).Association("SubUsers").Append(alice)
    if err != nil {
        panic(err)
    }

    var user User
    err = db.Preload("SubUsers").Preload("SuperUsers").First(&user, alice.ID).Error
    if err != nil {
        panic(err)
    }
    for _, u := range user.SubUsers {
        fmt.Println("Subuser", u.Name)
    }
    for _, u := range user.SuperUsers {
        fmt.Println("Superuser", u.Name)
    }
}

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM