Android背景服务中的领域

时间:2016-08-29 17:00:48

标签: android realm

我在Android应用程序中使用Realm。我通过CompletionEvent从谷歌驱动器收到通知,所以我需要在服务中修改我的域数据库。

我得到的例外是:

java.lang.IllegalStateException: Realm access from incorrect thread. Realm objects can only be accessed on the thread they were created.

我已经在我的Application类中设置了我的默认配置:

RealmConfiguration realmConfiguration = new RealmConfiguration.Builder(getApplicationContext())
            .deleteRealmIfMigrationNeeded()
            .build();
Realm.setDefaultConfiguration(realmConfiguration);

在我的服务的onCreate中,我得到了我的Realm实例:

mRealm = Realm.getDefaultInstance();

然后我在服务中使用这个领域实例:

mRealm.executeTransaction(realm -> {
        DocumentFileRealm documentFileRealm = realm.where(DocumentFileRealm.class)
                .equalTo("id", documentFileId)
                .findFirst();
        documentFileRealm.setDriveId(driveId);
    });

但是当执行最后一个时,应用程序会启动IllegalStateException。我不知道为什么。我不确定它是否与我在Android清单中声明服务的方式有关,所以我把它留在这里:

<service android:name=".package.UploadCompletionService" android:exported="true">
    <intent-filter>
        <action android:name="com.google.android.gms.drive.events.HANDLE_EVENT"/>
    </intent-filter>
</service>

是否可以通过后台服务调用Realm?我使用它的方式有什么问题?

提前致谢。

1 个答案:

答案 0 :(得分:1)

在IntentService中,您应该将onHandleIntent方法视为AsyncTask的doInBackground方法。

所以它在后台线程上运行,你应该确保在finally块中关闭Realm。

public class PollingService extends IntentService {
    @Override
    public void onHandleIntent(Intent intent) {
        Realm realm = null;
        try {
            realm = Realm.getDefaultInstance();
            // go do some network calls/etc and get some data 
            realm.executeTransaction(new Realm.Transaction() {
                @Override
                public void execute(Realm realm) {
                     realm.createAllFromJson(Customer.class, customerApi.getCustomers()); // Save a bunch of new Customer objects
                }
            });
        } finally {
            if(realm != null) {
                realm.close();
            }
        }
    }
    // ...
}

onCreate在UI线程上运行,因此您对Realm的初始化发生在另一个线程上,这是不行的。