mybatis插入数据后返回自增主键ID的两种实现方式

 更新时间:2024年05月18日 09:31:42   作者:随码去  
这篇文章主要介绍了mybatis插入数据后返回自增主键ID的两种实现方式,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教

mybatis插入数据后返回自增主键ID

开发过程中我们经常性的会用到许多的中间表,mybatis插入数据后返回自增主键的两种方式,

用于数据之间的对应和关联,这个时候我们关联最多的就是ID,我们在一张表中插入数据后级联增加到关联表中,我们数值的mybatis在插入数据后返回的是插入成功的条数,那么这个时候我们想要得到相应的新增数据的ID,该怎么办呢?

下面我们介绍二种方式来实现,一种是在xml文件种设置属性,另外一种就是使用注解来实现。

整体两种方法流程

1.使用注解@SelectKey,继承原生的方法insert来实现

这种方法是使用注解,不使用xml方法,使用继承原生的方法insert来实现,在注解里面写号SQL以及每个字段绑定的变量即可。

注解的方法为

@Override
        @Insert(" INSERT INTO `air_quality_index` (`districtId`, `monitorTime`, `Pm10`,`Pm25`,`monitoringStation`) VALUES (#{districtId}, NOW(), #{Pm10},#{Pm25},#{monitoringStation}))
@SelectKey(statement="select currval('air_quality_index_id_seq')"),keyProperty = "id",before=false,resultType = Long.class)
int insert(User user);
@SelectKey(statement="select currval('air_quality_index_id_seq')"),keyProperty = "id",before=false,resultType = Long.class)

其中select currval('air_quality_index_id_seq')")就是pgsql插入后返回的自增id,这种方式需要把数据库表的id设置成自增ID,这样注解就生效了

在使用的时候直接用

result = getBaseMapper().insert(user);

最后也得到了这个 自增的ID,当然了,我这个用的是pgsql,如果是mysql,在执行select LAST_INSERT_ID()得到的结果那么注解就得改一下:

@SelectKey(statement="select LAST_INSERT_ID()",keyProperty = "id",before = false,resultType = Long.class)

其中select LAST_INSERT_ID()就是mysql插入数据后,获取的当前的自增id。

2.在xml中定义useGeneratedKeys为true,返回主键id的值

keyProperty和keyColum分别代表

数据库记录主键字段和java对象成员属性名:在XML文件中要设置userGeneratedKeys="true" keyProperty="id"

<insert id="insertUser" useGeneratedKeys="true" keyProperty="id"> 
@Insert(" INSERT INTO `air_quality_index` (`districtId`, `monitorTime`, `Pm10`,`Pm25`,`monitoringStation`) VALUES (#{districtId}, NOW(), #{Pm10},#{Pm25},#{monitoringStation}))
</insert>

mybatis自动生成主键,返回自增主键 insert语句

对于表的主键自动生成的 insert语句 , 在不需要返回自增主键时 , 就和普通的insert语句没有区别 , 在需要的返回的时候 , 情况稍微有点不一样 , 故在此记录一下 . 在MyBatis中 ,  有两种方式编写SQL , 一种XML方式 , 一种是注解方式 .

首先在MYSQL中新建一张表 , 建表语句如下

CREATE TABLE `sys_user` (
  `id` int(11) NOT NULL AUTO_INCREMENT COMMENT '用户id',
  `user_name` varchar(64) DEFAULT NULL COMMENT '用户名',
  `password` varchar(64) DEFAULT NULL COMMENT '密码',
  `email` varchar(100) DEFAULT NULL COMMENT '邮箱',
  `info` text COMMENT '简介',
  `create_time` datetime DEFAULT NULL COMMENT '创建时间',
  PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COMMENT='用户表';

在使用主键自增的时候 ,  插入数据库后可能需要得到自增的主键值 , 然后使用这个值进行一些其他的操作 .

有些数据库提供主键自增(MYSQL , SQLSERVER) , 有些不提供(ORACLE) , 而是使用序列得到一个值 , 然后将这个值赋给 id , 再讲数据插入.

1.XML方式

  • 1.1返回自增主键
<insert id="insert1" useGeneratedKeys="true" keyProperty="id">
        insert into sys_user(user_name,password,email,info,create_time)
        values(#{userName},#{password},#{email},#{info},#{createTime})
    </insert>

使用useGeneratedKeys设置为true后 , MyBatis会使用JDBC的getGeneratedKeys方法取出由数据库内部生成的主键 .

获得主键值之后将其赋给keyProperty配置的 id 属性 .

当需要设置多个属性时 , 使用逗号隔开 , 这种情况下 还需要配置 keyColumn属性 , 按顺序指定数据库的列 , 这里列的值会和 keyProperty 配置的属性一一对应 .

由于要使用数据库返回的主键值 , 所以SQL上下两部分的列中去掉了 id 列和对于的 #{id} 属性

  • 1.2返回非自增主键

采用 <selectKey>标签获取主键的值 , 这种方式对提供和不提供主键自增功能的数据库同样适用

<insert id="insert2">
        insert into sys_user(user_name,password,email,info,create_time)
        values(#{userName},#{password},#{email},#{info},#{createTime})
        <selectKey keyColumn="id" resultType="int" keyProperty="id" order="AFTER">
            SELECT LAST_INSERT_ID()
        </selectKey>
    </insert>

selectKey标签的 keyColumn,keyProperty和上面useGeneratedKeys的用法和含义一样 , 这里的resultType用于设置返回值类型.

order 属性和数据库相关 , 在MYSQL 中 , order是AFTER , 因为当前及记录的主键值在insert语句执行成功之后才能拿到 , 而在ORACLE中,oder是BEFORE , 因为ORACLE需要先从序列取到值 , 再将其作为主键插入到数据库

2.注解方式

  • 2.1返回自增主键
@Insert("insert into sys_user(user_name,password,email,info,create_time)"
            +"values(#{userName},#{password},#{email},#{info},#{createTime})")
    @Options(keyColumn="id",keyProperty="id",useGeneratedKeys=true)
    int insert(SysUser user);

insert方法上除了 @Insert 注解之外 , 多了一个 @Option 注解 , 在这个注解上配置了useGeneratedKeys 和 keyProperty属性,用法和 XML 的方式一样 , 当需要配置多个列的时候 , 这个注解也提供了 keyColumn 属性 , 可以像XML中那样配置使用 . 

  • 2.2返回非自增
@Insert("insert into sys_user(user_name,password,email,info,create_time)"
            +"values(#{userName},#{password},#{email},#{info},#{createTime})")
    @SelectKey(statement="SELECT LAST_INSERT_ID()",
               keyProperty="id",
               resultType=Integer.class,
               before = false)
    int insert(SysUser user);

和XML的方式对比  , 只是XML中的order属性换成了 before属性 , before = true时 , 功能和order = before一样 , before = false时, 功能和order = after一样

总结

以上为个人经验,希望能给大家一个参考,也希望大家多多支持脚本之家。

相关文章

  • Java抛出异常与自定义异常类应用示例

    Java抛出异常与自定义异常类应用示例

    这篇文章主要介绍了Java抛出异常与自定义异常类,结合实例形式分析了Java针对错误与异常处理的try、catch、throw等语句相关使用技巧,需要的朋友可以参考下
    2019-03-03
  • springboot多环境进行动态配置的方法

    springboot多环境进行动态配置的方法

    这篇文章主要介绍了springboot多环境下如何进行动态配置,本文主要分享了如何在springboot的项目中使用多环境配置,重点是”spring.profiles.active“属性,需要的朋友可以参考下
    2022-06-06
  • Java实现的文件过滤代码分享(按后辍过滤)

    Java实现的文件过滤代码分享(按后辍过滤)

    这篇文章主要介绍了Java实现的文件过滤代码分享,本文通过后辍名过滤,代码写简洁,容易看懂,需要的朋友可以参考下
    2014-07-07
  • java基础之 “==”与“equals”区别详解

    java基础之 “==”与“equals”区别详解

    这篇文章主要介绍了java基础之 “==”与“equals”区别详解,需要的朋友可以参考下
    2020-02-02
  • java如何实现打印list对象占用多大内存

    java如何实现打印list对象占用多大内存

    在 Java 中精确计算 List 对象占用的内存大小需要考虑对象头,引用,数组开销和元素对象本身的大小,下面小编就来和大家详细介绍一下具体实现方式吧
    2025-07-07
  • idea更换jdk版本的完整步骤(附详细图文)

    idea更换jdk版本的完整步骤(附详细图文)

    idea很多地方都设置了jdk版本,不同模块的jdk版本也可能不一样,这篇文章主要介绍了idea更换jdk版本的完整步骤,通过文中介绍的步骤可以成功更换jdk版本,需要的朋友可以参考下
    2025-04-04
  • 关于druid配置参数的使用详解

    关于druid配置参数的使用详解

    这篇文章主要介绍了关于druid配置参数的使用,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教
    2025-06-06
  • Java框架Quartz中API、Jobs和Trigger详解

    Java框架Quartz中API、Jobs和Trigger详解

    这篇文章主要介绍了Java框架Quartz中API、Jobs和Trigger详解,JobDetail 对象是在将 job 加入 scheduler 时,由客户端程序(你的程序)创建的,它包含 job 的各种属性设置,以及用于存储 job 实例状态信息的 JobDataMap,需要的朋友可以参考下
    2023-11-11
  • springboot中RestTemplate发送HTTP请求的实现示例

    springboot中RestTemplate发送HTTP请求的实现示例

    RestTemplate是一个 spring-web 提供的执行HTTP请求的同步阻塞式工具类,本文就来介绍一下RestTemplate发送HTTP请求,具有一定的参考价值,感兴趣的可以了解一下
    2024-03-03
  • 使用SpringBoot读取Windows共享文件的代码示例

    使用SpringBoot读取Windows共享文件的代码示例

    在现代企业环境中,文件共享是一个常见的需求,Windows共享文件夹(SMB/CIFS协议)因其易用性和广泛的兼容性,成为了许多企业的首选,在Java应用中,尤其是使用Spring Boot框架时,如何读取Windows共享文件是一个值得探讨的话题,本文介绍了使用SpringBoot读取Windows共享文件
    2024-11-11

最新评论