首页 > 解决方案 > 核心数据无法合并更改崩溃 - 仅使用更大的 SQLite

问题描述

每当我尝试使用“无法合并更改”错误保存 Core Data MOC 时,我的应用程序就会崩溃。令我困惑的是,当 SQLite 文件在其中一个表上有 40k+ 条记录时,它只发生在我在初次启动时播种到应用程序的 SQLite 文件中。数据在 tableViews 中显示得非常好,我可以更新现有对象。我只是无法保存任何新对象而不会崩溃。

我采用了相同的 SQLite 文件(以维护相同的模式),删除了所有记录,在表上添加了少量记录,并且在应用程序中一切正常——我可以在视图控制器之间移动,添加新对象到核心数据实体,并将 MOC 保存在任何地方。

我在单例中使用核心数据堆栈。我已经记录了 MOC 的每个请求,并且主线程上只有一个请求。该应用程序非常基本,没有运行后台任务。我的构建目标是 iOS 13.0。

该错误也令人困惑,因为该错误甚至不在我插入 Core Data 的新对象上。它适用于 Core Data 中的一些其他现有对象,并且每次崩溃时都不同(例如,当我添加 BetaCat 或 DeltaCat 对象时会发生这种情况):

Fatal error: Unresolved error Error Domain=NSCocoaErrorDomain Code=133020 "Could not merge changes." UserInfo={conflictList=(
    "NSMergeConflict (0x600000025480) for NSManagedObject (0x600003661900) with objectID '0xe3afe1928ab74f71 <x-coredata://E62171B1-E38F-4BF5-B012-DB1842171304/TextCategory/p4>' with oldVersion = 0 and newVersion = <deleted> and old cached row = {\n    category = AlphaCat;\n    isLocked = \"<null>\";\n}"
), NSExceptionOmitCallstacks=true}, ["conflictList": <__NSArrayM 0x6000007e35d0>(
NSMergeConflict (0x600000025480) for NSManagedObject (0x600003661900) with objectID '0xe3afe1928ab74f71 <x-coredata://E62171B1-E38F-4BF5-B012-DB1842171304/TextCategory/p4>' with oldVersion = 0 and newVersion = <deleted> and old cached row = {
    category = AlphaCat;
    isLocked = "<null>";

我已经阅读了有关合并更改错误的所有内容,它似乎总是与多个 MOC 尝试保存数据相关的问题,并且存在似乎不适用于我的情况的冲突。

有谁知道为什么较大的 SQLite 文件而不是较小的 SQLite 文件存在问题?

编辑 我如何获取 MOC、设置实体属性和保存 MOC 的代码示例:

let newCategory = Category(context: CoreDataStack.getContext())
newCategory.attribute1 = textField.text!
newCategory.attribute2 = true

CoreDataStack.saveContext()

getContext() 只返回一个 persistentContainer.viewContext

和 saveContext() 是一个基本的:

if context.hasChanges {
            do {
                try context.save()
                
            } catch let error as NSError {
                let nserror = error as NSError
                fatalError("Unresolved error when saving MOC: \(nserror), \(nserror.userInfo)")                
            }
        }

标签: iosswiftsqlitecore-data

解决方案


如果你的上下文是共享的,最好提前设置它的mergePolicy,像这样:

yourContext.mergePolicy = NSMergeByPropertyStoreTrumpMergePolicy//OR: NSMergeByPropertyObjectTrumpMergePolicy

推荐阅读