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

Hibernate批量插入多条数据库记录仅成功插入1条如何解决

问题根因

  • 全程复用同一个Tx实例:你在循环外仅获取了1个Tx对象,循环内反复对同一个实例执行session.save()。Hibernate的save()方法仅对瞬时态对象(未关联Session、无有效主键标识)生成INSERT语句;当对象第一次执行save()后,会被关联到当前Session转为持久态,主键字段也会被赋值为数据库生成的值,后续再对同一个实例调用save(),只会触发UPDATE操作,不会生成新的INSERT。
  • 实体类交由Spring容器管控不合理:你通过applicationContext.getBean(Tx.class)获取实例,默认Spring管理的Bean是单例的,每次调用getBean都会返回同一个全局实例,无法生成新的独立对象。同时实体类作为数据载体,不需要被Spring容器管控,不需要添加@Component等Spring组件注解。
  • ID字段类型不规范:你使用基本数据类型int作为主键类型,默认值为0,Hibernate会将非0的ID判定为已存在的持久化标识,进一步阻断了新INSERT语句的生成,建议改为Integer包装类,符合JPA规范要求。

修复方案

  1. 移除Tx类上的Spring组件注解,改为业务代码中手动新建实例
  2. 循环内每次创建独立的Tx对象再执行保存操作
  3. 修正主键字段类型为Integer

修复后代码示例:

Session session = sessionFactory.openSession();
session.beginTransaction();
IntStream.range(0, 100).forEach(index -> {
    // 每次循环新建独立实例
    Tx tx = new Tx();
    // 按需设置字段值
    tx.setAaa("模板数据" + index);
    session.save(tx);
});
session.getTransaction().commit();
session.close();

如果确实需要从Spring容器获取Tx实例,可给Tx类添加@Scope("prototype")注解声明为多例,每次getBean都会返回新实例,但该方案不推荐用于实体类场景。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.10.03 17:45:03