You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

SQL Server 2012+中如何通过NamedParameterJdbcTemplate获取序列生成ID

解决SQL Server 2012 Sequence+默认约束下,Spring NamedParameterJdbcTemplate获取生成主键的问题

没问题,这个场景是可以拿到生成的ChangeEventId的,并不是用Sequence就做不到——只是需要调整一下NamedParameterJdbcTemplate.update的调用方式,明确告诉JDBC驱动要捕获哪个列的生成值。

核心原因

SQL Server的IDENTITY自增列会被JDBC驱动自动识别并返回生成值,但你用的是Sequence+默认约束的方式生成主键,这种情况驱动不会自动捕获生成值,必须显式指定要返回的主键列名。

具体实现步骤

  1. 编写插入SQL时,主键列使用DEFAULT或省略
    因为主键列已经通过默认约束关联了Sequence,所以插入时不需要手动赋值,要么直接省略该列,要么显式写DEFAULT:

    -- 方式1:省略主键列
    INSERT INTO YourTableName (Column1, Column2) VALUES (:col1, :col2);
    
    -- 方式2:显式使用DEFAULT
    INSERT INTO YourTableName (ChangeEventId, Column1, Column2) VALUES (DEFAULT, :col1, :col2);
    
  2. 调用update时指定返回的主键列名
    使用NamedParameterJdbcTemplate.update的重载方法,传入KeyHolder的同时,指定要返回的主键列名数组:

    String insertSql = "INSERT INTO ChangeEvents (EventName, EventTime) VALUES (:eventName, :eventTime)";
    
    // 构建参数
    SqlParameterSource params = new MapSqlParameterSource()
        .addValue("eventName", "用户登录事件")
        .addValue("eventTime", LocalDateTime.now());
    
    // 初始化KeyHolder
    KeyHolder keyHolder = new GeneratedKeyHolder();
    
    // 关键:最后一个参数指定要返回的主键列名
    namedParameterJdbcTemplate.update(insertSql, params, keyHolder, new String[]{"ChangeEventId"});
    
    // 获取生成的主键值(根据你的列类型调整,比如INT用intValue())
    Long generatedId = keyHolder.getKey().longValue();
    

注意事项

  • JDBC驱动版本:确保使用的SQL Server JDBC驱动版本不低于6.0,旧版本对Sequence的支持可能存在问题。
  • 列类型匹配:getKey()返回的是Number类型,要根据你主键列的实际类型(比如INT/BIGINT)转换为对应的数值类型。
  • 不要手动赋值主键:如果插入时手动给ChangeEventId赋值,那么KeyHolder拿到的就是你指定的值,而不是Sequence生成的。

内容的提问来源于stack exchange,提问作者ithinkisam

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.19 03:57:56