首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >spring boot jpa -生成并保存测试数据

spring boot jpa -生成并保存测试数据
EN

Stack Overflow用户
提问于 2017-02-15 19:56:38
回答 2查看 1.4K关注 0票数 1

我试图用大量的测试数据填充我的数据库,所以我写了一个CommandLineRunner来保存大约2k个实体。

它的工作-但它需要永远完成(5-10分钟)-我处理的方式错了吗?

代码语言:javascript
复制
@Component
public class DbSeederTest implements CommandLineRunner {

    @Autowired
    FirstRepo firstRepo;
    @Autowired
    SecondRepo secondRepo;
    @Autowired
    ThirdRepo thirdRepo;

    private List<FirstEnt> firstList = new ArrayList<>();
    private List<SecondEnt> secondList = new ArrayList<>();
    private List<ThirdEnt> thirdList = new ArrayList<>();


    private void generateTestData() {
          // generate alot of entities, and add them to the Lists
    }

    @Override
    public void run(String... args) throws Exception {

        System.out.println("saving ents...");

        generateTestData();

        try {

            firstRepo.save(firstList);
            secondRepo.save(secondList);
            thirdRepo.save(thirdList);

        } catch(Exception e) {
            e.printStackTrace();
        }

    }
}
EN

回答 2

Stack Overflow用户

发布于 2017-02-15 20:11:22

您可以尝试利用大容量插入特性。

您可以将hibernate属性定义为hibernate的SessionFactory属性之一

代码语言:javascript
复制
<property name="jdbc.batch_size">250</property>

使用此批处理设置,您应该有如下输出:

insert into Table(id , name) values (1, 'na1') , (2, 'na2') ,(3, 'na3').

而不是

代码语言:javascript
复制
insert into Table(id , name) values (1, 'na1');
insert into Table(id , name) values (2, 'na2');
insert into Table(id , name) values (3, 'na3');

在您的存储库保存方法中,您将持久化大约250个实体(您必须做一些测试,在您的应用程序中性能最佳的点是什么)。然后刷新会话以获得最佳性能,直到保存完所有数据:

代码语言:javascript
复制
public void save(List<Item> itemList){
  for ( int i=0; i<itemList.size(); i++ ) {   
      session.save(itemList.get(i));

      if ( i % 250 == 0 ) { //250, same as the JDBC batch size
          //flush a batch of inserts and release memory:
          session.flush();
          session.clear();
      }
  }
}
票数 0
EN

Stack Overflow用户

发布于 2017-02-15 20:22:46

您可以通过使用线程概念来减少所需的时间。

在调用所有存储库的save方法之前,您拥有调用generateTestData();之后的数据。

所以稍微修改一下代码

代码语言:javascript
复制
Thread thread1 = new Thread(()->firstRepo.save(firstList));
Thread thread2 = new Thread(()->secondRepo.save(secondList));
Thread thread3 = new Thread(()->thirdRepo.save(thirdList));
thread1.start();
thread2.start();
thread3.start();

使用Java8特性覆盖了Thread run方法。您可以在Java7中执行以下操作:

代码语言:javascript
复制
Thread thread1 = new Thread(new Runnable() {

    @Override
    public void run() {
        firstRepo.save(firstList);

    }
});

希望这能有所帮助。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/42248732

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档