gorm如何在已存在的一对一关系中进行插入操作?

huangapple go评论76阅读模式
英文:

gorm how to do insert with a has one relation that already exists

问题

以下是代码的翻译:

package main

import (
	"time"

	"gorm.io/driver/sqlite"
	"gorm.io/gorm"
	"gorm.io/gorm/logger"
)

type Country struct {
	ID        int
	Name      string `gorm:"uniqueIndex"`
	CreatedAt time.Time
	UpdatedAt time.Time
}
type Operator struct {
	ID        int
	CountryID int
	Country   Country
	Name      string
	Code      string
	CreatedAt time.Time
	UpdatedAt time.Time
}

func main() {
	config := gorm.Config{
		Logger: logger.Default.LogMode(logger.Info),
	}
	db, err := gorm.Open(sqlite.Open("test.db"), &config)

	if err != nil {
		panic(err)
	}

	db.AutoMigrate(&Country{}, &Operator{})
	test1 := Operator{Country: Country{Name: "Test"}, Name: "Test1", Code: "A"}
	db.Create(&test1)

	test2 := Operator{Country: Country{Name: "Test"}, Name: "Test2", Code: "B"}
	db.Create(&test2)

}

以上代码中,test1创建了一个新的Country和Operator,并且operator_id在xqlite数据库中是正确的。

然而,test2的operator_id被设置为0。我应该怎么做才能创建test2条目并使其引用一个现有的Country?

英文:
package main

import (
	"time"

	"gorm.io/driver/sqlite"
	"gorm.io/gorm"
	"gorm.io/gorm/logger"
)

type Country struct {
	ID        int
	Name      string `gorm:"uniqueIndex"`
	CreatedAt time.Time
	UpdatedAt time.Time
}
type Operator struct {
	ID        int
	CountryID int
	Country   Country
	Name      string
	Code      string
	CreatedAt time.Time
	UpdatedAt time.Time
}

func main() {
	config := gorm.Config{
		Logger: logger.Default.LogMode(logger.Info),
	}
	db, err := gorm.Open(sqlite.Open("test.db"), &config)

	if err != nil {
		panic(err)
	}

	db.AutoMigrate(&Country{}, &Operator{})
	test1 := Operator{Country: Country{Name: "Test"}, Name: "Test1", Code: "A"}
	db.Create(&test1)

	test2 := Operator{Country: Country{Name: "Test"}, Name: "Test2", Code: "B"}
	db.Create(&test2)

}

With the above code, test1 creates a new Country and Operator and the operator_id is correct in the xqlite database.

With test2 however, operator_id is set to 0. What should I do to create the test2 entry and have it refer to an existing Country ?

答案1

得分: 1

你对 db.Create(&test2) 的调用可能失败是因为 Country 上的 uniqueIndex 约束。确保检查错误!

你可能会发现,先向数据库插入一个单独的 Country 条目会起作用,像这样:

testCountry := Country{Name: "Test"}

if result := db.Create(&testCountry); result.Error != nil {
  // 处理 result.Error
}

根据我最近使用 Gorm 的经验,假设 db.Create 成功(始终检查错误!),它将填充 testCountry.ID。之后,像这样创建 test1test2

test1 := Operator{
  Country:   testCountry,
  CountryID: testCountry.ID,
  Name:      "Test1", 
  Code:      "A",
}

if result := db.Create(&test1); result.Error != nil {
  // 处理 result.Error
}

[...  test2 做同样的操作 ...]
英文:

Your call to db.Create(&test2) is likely failing due to the uniqueIndex constraint on Country. Make sure to check your errors!

What you may find to work is to insert a single Country entry into the DB first, like so:

testCountry := Country{Name: "Test"}

if result := db.Create(&testCountry); result.Error != nil {
  // do something with result.Error
}

Based on my most recent experience working with Gorm, db.Create will populate testCountry.ID assuming it succeeds (always check your errors!). After that, create test1 and test2 like so:

test1 := Operator{
  Country:   testCountry,
  CountryID: testCountry.ID,
  Name:      "Test1", 
  Code:      "A",
}

if result := db.Create(&test1); result.Error != nil {
  // do something with result.Error
}

[... do the same thing with test2 ...]

huangapple
  • 本文由 发表于 2021年10月30日 21:10:00
  • 转载请务必保留本文链接:https://go.coder-hub.com/69779917.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定