GORM Playground Link
https://github.com/go-gorm/playground/pull/1
Description
mysql数据库,当修改一对多的外键数据时,外键对应的数据会被双倍插入数据库。代码如下:
package main
import (
"fmt"
"gorm.io/driver/mysql"
"gorm.io/gorm"
)
type User struct {
ID int `gorm:"primaryKey"`
Name string `gorm:"index"`
PhoneList []Phone `gorm:"foreignKey:UserRefer"`
}
type Phone struct {
UserRefer int `gorm:"index"`
Number string
}
func main() {
dsn := "tempa:1920*1080@tcp(10.0.182.190:3306)/tempdb?charset=utf8mb4&parseTime=True&loc=Local"
db, err := gorm.Open(mysql.Open(dsn), &gorm.Config{})
if err != nil {
fmt.Println("can not connect db %s", err.Error())
}
err = db.AutoMigrate(&User{}, &Phone{})
if err != nil {
fmt.Println("can not update db %s", err.Error())
}
user := &User{
Name: "root",
}
result := db.Create(user)
if result.Error == nil {
fmt.Println("create record success ", result.RowsAffected)
}
user.PhoneList = []Phone{
{Number: "111111"},
{Number: "222222"},
{Number: "333333"},
{Number: "444444"},
}
result = db.Save(user)
if result.Error == nil {
fmt.Println("save record success ", result.RowsAffected)
}
fmt.Println(112233)
}
代码执行后phone表应该有4条数据,但是phone表有8条数据,有4条是重复数据。使用mysql数据库可以复现,sqlite数据库正常。其他数据库未测试。 phone表如下:
mysql> select * from phones;
+------------+--------+
| user_refer | number |
+------------+--------+
| 1 | 111111 |
| 1 | 222222 |
| 1 | 333333 |
| 1 | 444444 |
| 1 | 111111 |
| 1 | 222222 |
| 1 | 333333 |
| 1 | 444444 |
+------------+--------+
8 rows in set (0.00 sec)
Comment From: github-actions[bot]
The issue has been automatically marked as stale as it missing playground pull request link, which is important to help others understand your issue effectively and make sure the issue hasn't been fixed on latest master, checkout https://github.com/go-gorm/playground for details. it will be closed in 30 days if no further activity occurs. if you are asking question, please use the Question template, most likely your question already answered https://github.com/go-gorm/gorm/issues or described in the document https://gorm.io ✨ Search Before Asking ✨
Comment From: demoManito
How to solve
type Phone struct {
+ ID int `gorm:"primaryKey"`
UserRefer int `gorm:"index"`
Number string
}
user.PhoneList = []Phone{
+ {ID: 1, Number: "111111"},
+ {ID: 2, Number: "222222"},
+ {ID: 3, Number: "333333"},
+ {ID: 4, Number: "444444"},
- {Number: "111111"},
- {Number: "222222"},
- {Number: "333333"},
- {Number: "444444"},
}
db.Save(user) the following SQL will be executed:
INSERT INTO `phones` (`user_refer`,`number`,`id`) VALUES (1,'1111112',1),(1,'222222',2),(1,'333333',3),(1,'444444',4) ON DUPLICATE KEY UPDATE `user_refer`=VALUES(`user_refer`);
UPDATE `users` SET `name`='root' WHERE `id` = 1;
Describe
phones missing primary key or unique index.
you can refer to mysql ON DUPLICATE KEY UPDATE (https://dev.mysql.com/doc/refman/8.0/en/insert-on-duplicate.html).
Comment From: github-actions[bot]
This issue has been automatically marked as stale because it has been open 360 days with no activity. Remove stale label or comment or this will be closed in 180 days