MyBatis主键返回机制解析

关于 MyBatis 主键返回的深入解释

核心问题:信息隔离

数据库和应用程序是两个独立的系统:

  1. 数据库在服务器上执行 INSERT 操作并生成主键
  2. 应用程序在另一个进程或甚至另一台机器上运行
  3. 如果没有明确的机制,应用程序无法自动知道数据库生成了什么值

没有 @Options 或相关配置时的情况

// 假设没有配置主键返回
User user = new User();
user.setName("John");
userMapper.insert(user);// 此时 user.getId() 返回什么?
System.out.println(user.getId()); // 输出: null 或 0

在这种情况下,user 对象中的 id 字段不会被自动填充,因为 MyBatis 不知道需要将生成的主键值回填到对象中。

为什么需要显式配置

MyBatis 需要明确的指令来执行主键回填操作:

  1. useGeneratedKeys=true:告诉 MyBatis 使用 JDBC 的 getGeneratedKeys() 方法获取数据库生成的主键
  2. keyProperty="id":告诉 MyBatis 将获取到的主键值设置到参数对象的哪个属性中
// 使用 @Options 配置主键返回
@Options(useGeneratedKeys = true, keyProperty = "id")
@Insert("INSERT INTO users (name) VALUES (#{name})")
int insertUser(User user);// 使用后
User user = new User();
user.setName("John");
userMapper.insertUser(user);
System.out.println(user.getId()); // 输出: 123 (数据库生成的实际ID)

技术实现原理

当配置了主键返回后,MyBatis 和 JDBC 驱动会协同工作:

  1. MyBatis 通过 JDBC 执行 INSERT 语句
  2. JDBC 驱动调用 statement.getGeneratedKeys() 方法
  3. 数据库返回生成的主键值
  4. MyBatis 根据 keyProperty 配置,将主键值反射设置到参数对象的对应字段中

如果不配置主键返回,如何获取ID?

如果不使用 MyBatis 的主键返回功能,您仍然可以获取生成的主键,但需要额外的工作:

方法一:后续查询(不推荐)

userMapper.insert(user);
// 需要额外查询获取最后插入的ID(不可靠,特别是在高并发环境下)
Long id = userMapper.getLastInsertId();
user.setId(id);

方法二:数据库特定函数(局限性大)

-- 在INSERT语句后直接查询(MySQL示例)
INSERT INTO users (name) VALUES ('John');
SELECT LAST_INSERT_ID();

但这种方法需要执行两条SQL语句,且在高并发环境下可能不可靠。

为什么不能"直接getId提出"

您可能会想:“既然数据库生成了ID,我直接从对象中获取不就行了?”

问题在于:Java 对象和数据库之间没有自动的魔法连接。当您创建一个新的 User 对象时,它的 id 字段是 null(或默认值)。执行 INSERT 操作后,数据库中生成了ID,但这个值不会自动反映到您的 Java 对象中,除非有明确的机制(如 MyBatis 的主键返回功能)将它们连接起来。

总结

情况结果
不配置主键返回user.getId() 返回 null 或初始值,无法获取数据库生成的ID
配置主键返回user.getId() 返回数据库实际生成的ID,可以立即使用

因此,虽然数据库会自动生成自增主键,但应用程序仍然需要明确配置才能获取这个值。MyBatis 的 @Options 注解或其他主键返回配置正是为了搭建这座"桥梁",让应用程序能够方便地获取数据库生成的主键值。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。
如若转载,请注明出处:http://www.pswp.cn/bicheng/96810.shtml
繁体地址,请注明出处:http://hk.pswp.cn/bicheng/96810.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

【Python】Python内置函数大全解析(附源码)

目录专栏导读前言🚀 功能特性1. 全面的函数覆盖2. 多种查询工具3. 完整的测试验证🛠️ 使用方法基本使用交互式查询运行测试📚 支持的内置函数分类数学运算 (13个)类型转换 (8个)序列操作 (8个)迭代器 (6个)输入输出 (3个)对象操作 (31个)&am…

每日算法题推送

题目1:快乐数 我们先来结合实例看一下判断快乐数的整个过程: 结合题目可以知道,如果一个数是快乐数,那么这个数最终就会变成1,如果一个数不是快乐数,那么变化序列最终就会陷入循环。想一下,如果…

Oracle体系结构-数据文件(Data Files)

一、 数据文件的本质与原理 物理存储的基石: 数据文件是 Oracle 数据库在操作系统层面最核心、最基础的物理存储单元。它们是存储在服务器硬盘(或存储阵列)上的操作系统文件(如 .dbf, .ora 扩展名常见,但非强制&#x…

【C++练习】18.C++求两个整数的最小公倍数(LCM)

目录C求两个整数的最小公倍数(LCM)的方法方法一:利用最大公约数(GCD)计算代码实现方法二:逐次增加法代码实现方法三:质因数分解法代码实现方法比较处理大数和特殊情况改进版GCD方法实现 C求两个整数的最小公倍数(LCM)的方法 最小公倍数(LCM)是…

Linux网络:应用层协议http

前言 虽然我们说,应用层协议是我们程序猿自己定的。但实际上,已经有大佬们定义了一些现成的,又非常好用的应用层协议,供我们直接参考使用.HTTP(超文本传输协议)就是其中之一。 我们之前已经学了UDP与TCP套接字的简单使用,以及讲解了进程间的各种关系&a…

ffmpeg推流测试

提示:文章写完后,目录可以自动生成,如何生成可参考右边的帮助文档 文章目录前言一、操作步骤1.测试12.测试2总结前言 提示:这里可以添加本文要记录的大概内容: 环境信息: 摄像头:usb摄像头 &a…

Docker的使用及核心命令

文章目录Docker基础概念镜像管理命令镜像查看和搜索镜像下载和删除镜像构建容器生命周期管理创建和启动容器容器控制命令容器清理容器交互和调试进入容器文件操作日志和监控数据管理数据卷(Volume)绑定挂载网络管理网络基础操作端口映射Dockerfile和Dock…

考研408计算机网络第36题真题解析(2021-2023)

(2023.36)在使用 CSMA/CD 协议的环境中,使用截断二进制指数退避算法,来选择重传时机,算法 有如下规定: (1)基本的退避时间为争用期 2τ,假设某网络具体的争用期为 51.2us…

Asio C++ Library是用来做什么的

hriskohlhoff/asio 是由 Chris Kohlhoff 主导维护的开源 C 库,专注于提供高效、跨平台的异步 I/O 支持,广泛应用于网络编程、并发控制和高性能系统开发。 📘 项目概述 项目名称:Asio C Library 下载地址:https://down…

ac791的按键ad_channel

每次ad_channel这个参数都要给我一定的迷惑性,让我以为这是通道的数量

机器人巡检与巡逻的区别进行详细讲解和对比

机器人巡检与巡逻的区别进行详细讲解和对比 尽管这两个词经常被混用,但在技术和应用层面上,它们有着本质的区别。核心区别在于:巡检是“深度体检”,而巡逻是“治安巡查”。 以下将从多个维度进行详细讲解和对比。 一、核心概念与目…

先进电机拓扑及控制算法介绍(3)——以“数据”驱动电机实现真正的无模型

1. 背景介绍 之前已经介绍过“无模型预测控制(Model-Free Predictive Control/MFPC)”中的“无模型预测电流控制(Model-Free Predictive Current Control/MFPCC)”,可参考下面知乎。 https://zhuanlan.zhihu.com/p/6…

C primer plus (第六版)第十一章 编程练习第5,6题

题目:5.设计并测试⼀个函数,搜索第1个函数形参指定的字符串,在其中查找第2个函数形参指定的字符⾸次出现的位置。如果成功,该函数返指向该字符的指针,如果在字符串中未找到指定字符,则返回空指针…

Altium Designer(AD)PCB丝印批量修改

目录 1 Altium Designer(AD)PCB丝印的字体批量修改 1.1选中所有丝印 1.1.1选中一个丝印:鼠标左键点击 1.1.2查找相似对象:鼠标右键或快捷键N 1.1.3如下图所示丝印被全部选中 1.2丝印字体信息修改 1.2.1打开属性面板——>位置/属性/字体修改 1.2.2丝印字体修改 1.2.…

AI+华为HarmonyOS开发工具DevEco Studio详细安装指南

作者:长江支流 日期:2025-09-13 第一部分:AI工具使用 一、如何使用DeepSeek帮助自己的工作? (一)提示词 为了与时俱进,充分利用最新技术、提高效率,采用AI生成部分材料&#xf…

【Ambari监控】— API请求逻辑梳理

附录:完整内容和源代码下载请参照 https://doc.janettr.com/ 一、前序章节回忆 我们在前面章节拆解了 Collector 的启动过程,并定位了控制器 TimelineWebServices。 本节聚焦 Collector 对外暴露的 REST 服务,搭建「接口全景图」。 二、接口…

论文阅读 2025-9-13 论文阅读随心记

随便记录一下最近阅读的几篇论文 1. Does DINOv3 Set a New Medical Vision Standard? 第一章 动机 (Motivation) 自然图像领域的成功范式:大型语言模型(LLMs)和视觉基础模型(如 DINO 系列)证明,通过自监督…

Avalonia 基础导航实现:从页面切换到响应式交互全指南

在 Avalonia 开发中,导航功能是构建多页面应用的核心需求。Avalonia 无需依赖第三方库,仅通过内置控件与 MVVM 模式即可实现灵活的页面切换。本文将以 “基础导航” 为核心,从 ViewModel 与 View 设计、导航逻辑实现,到样式美化与…

UniApp 分包异步化配置及组件引用解决方案

具体参考微信小程序文档基础能力 / 分包加载 / 分包异步化 一、分包页面组件配置 在 UniApp 的pages.json中,为分包页面(或主包如 tabbar 页面)配置异步组件时,需同时设置usingComponents和componentPlaceholder: {&…

系统核心解析:深入操作系统内部机制——进程管理与控制指南(一)【进程/PCB】

♥♥♥~~~~~~欢迎光临知星小度博客空间~~~~~~♥♥♥ ♥♥♥零星地变得优秀~也能拼凑出星河~♥♥♥ ♥♥♥我们一起努力成为更好的自己~♥♥♥ ♥♥♥如果这一篇博客对你有帮助~别忘了点赞分享哦~♥♥♥ ♥♥♥如果有什么问题可以评论区留言或者私信我哦~♥♥♥ ✨✨✨✨✨✨个人…