Wednesday, 6 July 2011

Use of entityManager flush during persist

We encountered a scenario where persisting some duplicate data correctly caused a data integrity issue and needed to translate that into an application exception. Our exception was declared within the service operation by wrapping the call to the DAO within a try-catch block and catching any exception. During runtime we noticed that our exception wasn’t being thrown. It transpired that as the service operation was marked as transactional, the persisting of the data and execution of the SQL statements was not occurring when the DAO operation completed but after the service operation (i.e. end of the transaction). Hence the constraint violation exception was not being caught within the service operation as had been planned. For cases like this where an exception is required to be caught the solution is to flush the SQL cache immediately after persisting the data.

@Transactional
@Override
public void storeTopupVouchers(List list) throws CreateVoucherException {
  try {
    TopUpDAO.create(list);
  } catch (Exception e) {
    throw new CreateVoucherException("Failed to create voucher -
    "+e.getMessage(),e);
  }
}


@Override
public void create(List list) {
  for(Topup topup : list) {
    em.persist(topup);
  }
    em.flush();
}

Reference: http://stackoverflow.com/questions/4275111/correct-use-of-flush-in-jpa-hibernate

No comments:

Post a Comment