gorm获取最后插入的数据ID的方法 LastInsertId

gorm这个ORM框架和我们常见的其他框架不太一样,他是没有LastInsertId这个方法的, 因为他内部使用了反射写数据的技术,他在数据插入成功后会将当前入库的数据写入到你插入的数据模型中, 所以我们在插入完成数据后直接调用 xx.Id 方法即可获取插入后的数据ID。

示例:

// 测试
	user:= entity.SysUser{}
	user.Username="zhansan"

	global.GetTx("sys_user").Create(&user) //数据插入
	lastId:= user.ID // 获取最后插入的数据ID

这里的 entity.SysUser 就是你的数据库表的实体对象定义, 在使用Create方法或者Save方法插入数据后gorm会将当前插入的数据对应的数据库中的记录都通过反射写入到user这个对象上面,我们要获取最后插入的ID或者当前插入数据的其他信息都可以通过这个对象获取, 这个还是很方便的,比使用LastInsertId 更加精简!

gorm反射写入数据核心代码示例

    tx.Statement.Dest = value



	// assign stmt.ReflectValue
	if stmt.Dest != nil {
		stmt.ReflectValue = reflect.ValueOf(stmt.Dest)
		for stmt.ReflectValue.Kind() == reflect.Ptr {
			if stmt.ReflectValue.IsNil() && stmt.ReflectValue.CanAddr() {
				stmt.ReflectValue.Set(reflect.New(stmt.ReflectValue.Type().Elem()))
			}

			stmt.ReflectValue = stmt.ReflectValue.Elem()
		}
		if !stmt.ReflectValue.IsValid() {
			db.AddError(ErrInvalidValue)
		}
	}

### 使用 Golang 操作 MySQL 的基本流程 #### 1. 数据库连接初始化 在使用 Go 编程语言操作 MySQL 数据库之前,需要先完成数据库的连接配置。以下是通过标准 `database/sql` 包和第三方驱动程序实现的一个示例: ```go package main import ( "database/sql" "fmt" "log" _ "github.com/go-sql-driver/mysql" // 导入 MySQL 驱动包 ) func main() { dsn := "user:password@tcp(127.0.0.1:3306)/testdb?charset=utf8mb4&parseTime=True&loc=Local" db, err := sql.Open("mysql", dsn) if err != nil { log.Fatal(err) } defer db.Close() err = db.Ping() if err != nil { log.Fatal(err) } fmt.Println("Connected to the database!") } ``` 上述代码展示了如何通过 DSN (Data Source Name) 创建并测试与 MySQL 数据库的连接[^2]。 --- #### 2. 单行查询 对于简单的单行查询需求,可以利用 `QueryRow()` 方法执行 SQL 查询语句,并解析返回的结果集。 ```go var name string err := db.QueryRow("SELECT name FROM users WHERE id=?", 1).Scan(&name) if err != nil { switch { case err == sql.ErrNoRows: fmt.Println("User not found.") default: log.Fatal(err) } } else { fmt.Printf("User's name is %s\n", name) } ``` 此部分实现了基于特定条件检索单一记录的功能。 --- #### 3. 多行查询 当需要获取多条记录时,则应采用 `Query()` 方法来处理结果集合中的每一项数据。 ```go rows, err := db.Query("SELECT id, name FROM users") if err != nil { log.Fatal(err) } defer rows.Close() for rows.Next() { var id int var name string if err := rows.Scan(&id, &name); err != nil { log.Fatal(err) } fmt.Printf("ID: %d, Name: %s\n", id, name) } if err := rows.Err(); err != nil { log.Fatal(err) } ``` 这里提供了遍历整个结果集的方式。 --- #### 4. 插入、更新与删除操作 除了读取之外,还可以对数据库内的现有信息实施修改动作,比如新增一条记录或者移除某些不符合要求的数据项。 ##### 插入新纪录 ```go result, err := db.Exec("INSERT INTO users(name, age) VALUES (?, ?)", "Alice", 30) if err != nil { log.Fatal(err) } lastInsertId, _ := result.LastInsertId() fmt.Println("Inserted user with ID:", lastInsertId) ``` ##### 更新已有资料 ```go res, err := db.Exec("UPDATE users SET age=? WHERE name=?", 35, "Alice") if err != nil { log.Fatal(err) } affected, _ := res.RowsAffected() fmt.Println("Updated", affected, "row(s)") ``` ##### 删除指定对象 ```go _, err = db.Exec("DELETE FROM users WHERE name=?", "Bob") if err != nil { log.Fatal(err) } fmt.Println("Deleted Bob from users table") ``` 这些片段分别演示了向表格中添加元素、调整属性值以及清除节点的过程。 --- #### 5. 预处理语句防止 SQL 注入攻击 为了增强安全性,推荐使用预编译好的命令代替直接拼接字符串形式构建最终指令文本。 ```go stmt, err := db.Prepare("INSERT INTO users(name,age) values(?,?)") // 安全参数化查询 if err != nil { log.Fatal(err) } defer stmt.Close() insertedResult, err := stmt.Exec("Charlie", 28) if err != nil { log.Fatal(err) } newUserId, _ := insertedResult.LastInsertId() fmt.Println("New User Created With Id:", newUserId) ``` 这种方法有效规避了许多潜在风险隐患的同时也提高了性能表现[^1]。 --- #### 6. ORM 工具简化开发体验 如果希望进一步减少样板代码量的话,那么引入像 **GORM** 这样的高级框架将会是一个不错的选择方案之一。 下面给出一段关于怎样借助它快速搭建起基础架构的例子: ```go package main import ( "fmt" "gorm.io/driver/mysql" "gorm.io/gorm" ) type Product struct { gorm.Model Code string Price uint } func main() { dsn := "user:password@tcp(127.0.0.1:3306)/dbname?charset=utf8mb4&parseTime=True&loc=Local" db, err := gorm.Open(mysql.Open(dsn), &gorm.Config{}) if err != nil { panic("failed to connect database") } // 自动迁移模式 err = db.AutoMigrate(&Product{}) if err != nil { fmt.Println(err) return } // Create product := Product{Code: "D42", Price: 100} result := db.Create(&product) fmt.Println(result.Error) // 输出任何错误消息 fmt.Println(product.ID) // 返回插入后的主键值 } ``` 这段脚本不仅完成了常规的任务而且还包含了额外的一些特性支持,例如模型定义自动生成对应的物理存储结构等等[^3]^. ---
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

tekin

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值