使用JPA/EJB3批量插入

Raj*_*aja 21 java orm hibernate jpa batch-insert

JPA/EJB3框架是否提供了批量插入操作的标准方法......?我们使用hibernate作为持久性框架,所以我可以回退到Hibernate Session并使用组合session.save()/ session.flush()实现批量插入.但是想知道EJB3是否支持这个......

Pas*_*ent 21

JPA和Hibernate都没有为批量插入提供特殊支持,而使用JPA批量插入的习惯用法与Hibernate相同:

EntityManager em = ...;
EntityTransaction tx = em.getTransaction();
tx.begin();

for ( int i=0; i<100000; i++ ) {
    Customer customer = new Customer(.....);
    em.persist(customer);
    if ( i % 20 == 0 ) { //20, same as the JDBC batch size
        //flush a batch of inserts and release memory:
        em.flush();
        em.clear();
    }
}

tx.commit();
session.close();
Run Code Online (Sandbox Code Playgroud)

在这种情况下使用Hibernate的专有API并不能提供IMO的任何优势.

参考

  • JPA 1.0规范
    • 第4.10节"批量更新和删除操作"
  • Hibernate Core参考指南


Lok*_*oki 5

具体来说,对于hibernate,核心手册的第13章解释了这些方法.

但是你说你希望EJB方法通过Hibernate,所以实体管理器文档在这里也有一章.我建议您同时阅读(核心和实体经理).

在EJB中,它只是使用EJB-QL(有一些限制).如果您需要更多灵活性,Hibernate提供了更多的机制.


Tho*_*Tho 5

使用中等记录编号,您可以使用这种方式:

em.getTransaction().begin();
for (int i = 1; i <= 100000; i++) {
     Point point = new Point(i, i);
     em.persist(point);
     if ((i % 10000) == 0) {
          em.flush();
          em.clear();
     }
}
em.getTransaction().commit();
Run Code Online (Sandbox Code Playgroud)

但是对于大量记录,您应该在多个事务中执行此任务:

em.getTransaction().begin();
for (int i = 1; i <= 1000000; i++) {
      Point point = new Point(i, i);
      em.persist(point);
      if ((i % 10000) == 0) {
          em.getTransaction().commit();
          em.clear();          
          em.getTransaction().begin();
      }
}
em.getTransaction().commit();
Run Code Online (Sandbox Code Playgroud)

参考:JPA 批处理存储