在后台线程中保存对象时的RLMException

时间:2017-01-27 23:24:28

标签: swift realm realm-mobile-platform

在后台异步保存对象时,我得到 RLMException:'无法添加来自不同Realm的对象。但是,如果删除异步代码,相同的保存工作正常。

此对象与现有对象有关系。例如:

class Person: Object {
  name: String
  school: School
}

class School: Object {
  name: String
}

let person = new Person()
person.name = "John"
person.school = school // Existing object selected from a dropdown.

DispatchQueue.global().async {
    do {
        let realm = try Realm!

        try realm.write {
            realm.add(person, update: true)
        }

        DispatchQueue.main.async {
            // Success!
        }
    } catch let error as NSError {
        DispatchQueue.main.async {
            // Error!
        }
    }
}

此代码导致崩溃。但是,如果我删除DispatchQueye.global()。async,一切正常。我遇到了一些线程问题吗?

注意:school对象已预先存在,并从Results<School>集合中选择。

1 个答案:

答案 0 :(得分:6)

领域Object实例一旦被保存到Realm就无法在线程之间移动。由于school将是在主线程上实例化的对象,因此您可以通过将其附加到非持久化对象并将该批次移动到后台线程来创建冲突。

要解决此问题,您需要使用Realm's thread reference feature制作school对象的后台版本。

此外,除非您在主线程上有特定原因要创建Person,否则我也建议将其创建移至后台线程。

let schoolRef = ThreadSafeReference(to: school)

DispatchQueue.global().async {
    do {
        let realm = try Realm!

        let person = new Person()
        person.name = "John"
        person.school = realm.resolve(schoolRef)!

        try realm.write {
            realm.add(person, update: true)
        }

        DispatchQueue.main.async {
            // Success!
        }
    } catch let error as NSError {
        DispatchQueue.main.async {
            // Error!
        }
    }
}