androidrealmrealm-java

How to handle Realm transactions on Android


In several pieces of sample code out there, I've seen patterns that look like this:

try (Realm realm = Realm.getDefaultInstance()) {
  realm.beginTransaction();
  workWithRealmData();
  realm.commitTransaction();
}

The question is - is this safe? If the "workWithRealmData()" function throws an exception, the transaction won't be canceled. But we are closing the Realm anyway in the finally of the try-with-resources.

A safer construction might look like the following:

try (Realm realm = Realm.getDefaultInstance()) {
  realm.beginTransaction();
  try {
    workWithRealmData();
    realm.commitTransaction();
  } finally {
    if (realm.isInTransaction()) {
      realm.cancelTransaction();
    }
  }
}

That looks safer - but also looks significantly nastier to code for all callsites.

So really this boils down to - is it safe to ignore cancelTransaction if the Realm is closed immediately afterwards, or not? If not, what could go wrong?


Solution

  • You can use executeTransaction(Realm.Transaction) method which automatically cancels the synchronous transaction in case of error.

    try(Realm r = Realm.getDefaultInstance()) {
        r.executeTransaction((realm) -> {
            workWithRealmData();
        });
    }