Realm IllegalStateException

时间:2017-12-05 12:35:46

标签: android realm instance

我尝试使用realm作为API下载数据的持久化方法。我收到错误:*

  

引起:java.lang.IllegalStateException:此Realm实例具有   已关闭,使其无法使用。

我不知道我对持久性方法做错了什么。我的坚持下课是下一个:

public class PersistenceManager {

    @Inject
    public PersistenceManager(){}

    public void saveHabitants(final List<Habitant> habitants){

        Realm realm = Realm.getDefaultInstance(); // opens db
        try {
            realm.executeTransaction(new Realm.Transaction() {
                @Override
                public void execute(Realm realm) {
                    realm.insertOrUpdate(habitants);
                }
            });
        } finally {
            realm.close();
        }

    }

    public void saveHabitant(final Habitant habitant){

        Realm realm = Realm.getDefaultInstance();
        try {
            realm.executeTransaction(new Realm.Transaction() {
                @Override
                public void execute(Realm realm) {
                    realm.insertOrUpdate(habitant);
                }
            });
        } finally {
            realm.close();
        }

    }

    public List<Habitant> loadHabitants(){

        Realm realm = Realm.getDefaultInstance();
        List<Habitant> results;

        try {
            results = realm.where(Habitant.class).findAll();
        } finally {
            realm.close();
        }

        return results;
    }

    public List<Habitant> loadHabitants(int indexFrom, int limit){

        Realm realm = Realm.getDefaultInstance();
        List<Habitant> results;

        try {
            results = realm.where(Habitant.class).findAll();
            results.subList(indexFrom, limit);
        } finally {
            realm.close();
        }

        return results;
    }

    public Habitant loadHabitant(long id){

        Realm realm = Realm.getDefaultInstance();
        Habitant result;

        try {
            result = realm.where(Habitant.class).equalTo("id", id).findFirst();
        } finally {
            realm.close();
        }

        return result;
    }


}

当我使用方法loadHabitants(int indexFrom, int limit)时,我收到此错误。

1 个答案:

答案 0 :(得分:1)

只要在给定线程上至少有一个打开的Realm实例,就可以通过延迟加载(每个访问器)访问RealmResults。

我其实打算参考文档,但由于某些原因我无法找到它?无论如何,懒惰地访问RealmResults,因此当没有打开的Realm实例时,它变得无效,并且无法再访问。对于RealmObjects也是如此。

The docs请说:

  

...通过惰性缓存访问RealmObjects和RealmResults ...

因此,如果关闭与之关联的线程本地Realm实例,则无法返回托管的RealmResults,并期望它保持打开状态。

两种解决方案:

1。)参考关于如何在UI线程和后台线程上正确管理Realm生命周期的documentation

2。)使用realm.copyFromRealm(),它急切地评估整个数据集,创建它的分离副本。请注意,这不是免费操作,如果在UI线程上使用copyFromRealm(),较大的数据集很容易导致UI线程冻结。

public List<Habitant> loadHabitants(int indexFrom, int limit){
    try(Realm realm = Realm.getDefaultInstance()) {
        List<Habitant> results = realm.where(Habitant.class).findAll();
        results = new ArrayList<>(results.subList(indexFrom, limit));
        for(int i = 0, size = results.size(); i < size; i++) {
            results.set(i, realm.copyFromRealm(results.get(i)));
        }
        return Collections.unmodifiableList(results);
    }
}