hibernate关系映射/加速批量插入

我有5个MySQL InnoDB表: Test,InputInvoice,InputLine,OutputInvoice,OutputLine每个表都映射并在Hibernate中运行。 我玩过使用StatelessSession / Session和JDBC批量大小。 我删除了任何生成器类以让MySQL处理id生成 – 但它仍然执行速度很慢。 这些表中的每一个都在java类中表示,并相应地映射到hibernate中。 目前,当需要将数据写出来时,如果我使用StatelessSession,我会遍历对象并执行session.save(Object)session.insert(Object) 。 当我的行数达到最大jdbc批量大小(50)时,我也进行刷新和清除(当使用Session时)。

  1. 如果我在拥有对象并执行session.save(master)而不是每个对象的’parent’类中拥有它们会更快吗?
  2. 如果我在主/容器类中使用它们,我如何在hibernate中映射它以反映关系? 容器类实际上不是它自己的表,而是一个基于两个索引run_id(int)和line(int)的关系。
  3. 另一个方向是:如何让Hibernate进行多行插入?

ID生成策略对于Hibernate中的批量插入至关重要。 特别是,IDENTITY生成通常不起作用(请注意,AUTO通常也会映射到IDENTITY)。 这是因为在批量插入期间,Hibernate有一个名为“requiresImmediateIdAccess”的标志,表示是否立即生成ID; 如果是,则禁用批处理。

您可以在DEBUG级别日志中轻松发现“立即执行标识插入” – 这意味着它已跳过批处理,因为它被告知插入后需要立即生成ID。

通常起作用的生成策略是TABLE和SEQUENCE,因为Hibernate可以预先生成ID,从而允许批量插入。

快速查看批量插入是否有效的方法是激活DEBUG级日志,因为BatchingBatcher将明确告诉您正在执行的批量大小(“执行批量大小:”+ batchSize)。

此外,以下属性对于实现批量插入很重要。 我不敢说他们是必需的,因为我不够Hibernate专家这么做 – 也许这只是我的特殊配置 – 但根据我的经验,他们仍然需要:

 hibernate.order_inserts = true hibernate.order_updates = true 

这些属性记录很差,但我相信他们所做的是使SQL INSERT和UPDATE语句能够正确分组以进行批处理执行; 我想这可能是你想要的多排插页。 如果我错了,请不要开枪,我记忆中的回忆。

我也会继续并假设您设置以下属性; 如果没有,这应该作为提醒:

 hibernate.jdbc.batch_size = xx 

其中xx是您所需的批量大小,当然。

对我来说,最后的解决方案是使用voetsjoeba的响应作为跳跃点。 我的hibernate配置使用以下选项:

 hibernate.order_inserts = true hibernate.order_updates = true 
  • 我从使用Session变为StatelessSession

  • 重新排序Java代码以一次处理批处理表中的所有元素。 所以表x,然后表y等等。

  • 从每个class级中删除了 。 Java现在创建它并将其分配给对象

  • 创建的逻辑允许我确定是否只是设置了一个id而不是将“空”行写入数据库

  • 最后,我在他们的hibernate定义中为我的类启用了dynamic-insert ,如下所示: