我正在开发一个程序,该程序使用带有容器管理事务的 JTA/EclipseLink 2.3.x JPA 从文件中读取并逐行插入 Oracle 11g 数据库。
我已经开发了下面的代码,但我对失败的行需要知道并手动修复这一事实感到困惑。
public class CreateAccount {
@PersistenceContext(unitName="filereader")
private EntityManager em;
private ArrayList<String> unprocessed;
public void upload(){
//reading the file into unprocessed
for (String s : unprocessed) {
this.process(s);
}
}
private void process(String s){
//Setting the entity with appropriate properties.
//Validate the entity
em.persist(account);
}
}
第一个版本需要几秒钟来将 5000 行提交到数据库,因为它似乎利用了缓存准备好的语句。当所有要持久化的实体都有效时,这可以正常工作。但是,我担心即使我验证了实体,仍然有可能由于各种意外原因而失败,并且当任何实体在提交期间抛出异常时,我找不到导致它的特定记录,并且所有实体都已经回滚。
我尝试了另一种方法,即在进程(String s)中使用以下代码启动一个新事务并为每一行提交而不使用托管事务。
for (String s : unprocessedLines) {
try {
em.getTransaction().begin();
this.process(s);
em.getTransaction().commit();
} catch (Exception e) {
// Any exception that a line caused can be caught here
e.printStackTrace();
}
}
第二个版本非常适合记录错误行,因为捕获并处理了由单个行引起的异常,但是将相同的 5000 行提交到数据库需要 300 多秒。处理大文件时所花费的时间是不合理的。
是否有任何解决方法可以让我快速检查和插入记录,同时收到任何失败行的通知?