SwiftUI - Realm:无法从中删除关键路径的观察者,因为它未注册为观察者

时间:2021-02-20 18:56:39

标签: exception swiftui realm

我在最新的 Realm 版本 10.6.0 中遇到了一个奇怪的问题。当我尝试删除跨多个 NavigationView 使用的对象时,我遇到了错误:

Cannot remove an observer <RealmSwift.SwiftUIKVO 0x6000000c00e0> for the key path \"myId\" from <RLM:Unmanaged MyModel 0x6000037fa8a0> because it is not registered as an observer.

我组装了一个超级简单的演示项目来重现错误。只需运行它并转到第三个视图,在您尝试返回之前点击该按钮。

import SwiftUI
import RealmSwift //minimum version 10.6.0 Realm and 10.5.0 RealmDatabase from https://github.com/realm/realm-cocoa

//MARK: - Realm Model

@objcMembers class MyModel: Object, ObjectKeyIdentifiable {
    dynamic var myId = ""
    dynamic var text = ""
    dynamic var desc = ""
    
    override static func primaryKey() -> String? {
        return "myId"
    }
    
}

//MARK: - Root View

struct ContentView: View {
    
    @ObservedResults(MyModel.self) var myModel
    
    @State var navigationViewIsActive: Bool = false
    
    var body: some View {
        
        NavigationView {
            VStack {
                
                Text("Click the plus in the toolbar to add some test entries")
                
                List {
                    ForEach(myModel) { model in
                        
                        NavigationLink(destination: SecondView(navigationViewIsActive: $navigationViewIsActive, selectedEntry: model), isActive: $navigationViewIsActive)
                        {
                            Text(model.text)
                        }
                        
                    }
                }
            }
            .toolbar {
                
                ToolbarItem(placement: .navigationBarLeading){
                    Button(action: {
                        
                        let model = MyModel()
                        model.myId = UUID().uuidString.lowercased()
                        model.text = UUID().uuidString.lowercased()
                        
                        do {
                            let realm = try Realm()
                            try realm.write {
                                realm.add(model, update: .modified)
                                print("adding new entry to models")
                            }
                        } catch let error {
                            print(error.localizedDescription)
                        }
                        
                        
                    }, label: {
                        Image(systemName: "plus")
                    })
                }
                
            }
            
        }
    }
}


//MARK: - SecondView

struct SecondView: View {
    
    @Binding var navigationViewIsActive: Bool
    
    @ObservedRealmObject var selectedEntry: MyModel
    
    @State var showThirdView = false
    
    var body: some View {
        
        VStack {
            Text("Selected Entry:")
            Text(selectedEntry.text)
            Button(action: {
                print("show third view")
                self.showThirdView = true
            }, label: {
                Text("Click to show Third View")
            })
        }
        
        NavigationLink(destination: ThirdView(navigationViewIsActive: $navigationViewIsActive, selectedEntry: selectedEntry), isActive: $showThirdView, label: {EmptyView()})
        
    }
}

//MARK: - Third View

struct ThirdView: View {
    
    @Binding var navigationViewIsActive: Bool
    
    @ObservedRealmObject var selectedEntry: MyModel
    
    var body: some View {
        VStack {
        Text("Selected Entry:")
        Text(selectedEntry.text)
        Button(action: {
            print("delete this entry")
            self.navigationViewIsActive = false
            
            
            do {
                let realm = try Realm()
                try realm.write {

                    let myEntryIwantToDelete = realm.objects(MyModel.self).filter("myId=%@", selectedEntry.myId)

                    realm.delete(myEntryIwantToDelete)
                }
                print("deleting entry via realm")
            } catch {
                print("Error")
            }
            
            
            
        }, label: {
            Text("Delete this entry and go back to root view")
        })
          Text("after i click this button and navigate back i get the error")
        }
    }
}

我的设置: 模拟器:iPhone 11 iOS 14.4 代码 12.4 BigSur 11.1 / MacBook Pro M1

非常感谢!

1 个答案:

答案 0 :(得分:1)

错误修复将在下一个 Realm 版本中发布。为 KVO 订阅添加保护以防止多个观察者被移除。

错误报告在这里

Cannot remove an observer for key path because it is not registered as an observer

和可能的修复

Add guard to KVO subscription to prevent multiple observer removals to occur unnecessarily #7132

相关问题