核心数据 - 重新启动应用程序时部分数据丢失

Posted

技术标签:

【中文标题】核心数据 - 重新启动应用程序时部分数据丢失【英文标题】:Core Data - partial data loss when relaunching app 【发布时间】:2016-08-17 23:31:38 【问题描述】:

我有一个包含多个实体的单一模型的 Core Data 应用程序。出于这个问题的目的,我们将模型称为“Person”,并拥有实体“name”(字符串)、“age”(int)、“occupation”(字符串)和“description”(字符串)。

例如,我可以添加一个新的人。我设置了他们的姓名、年龄、职业和描述。我通过检查NSManagedObjectContextObjectsDidChangeNotification userInfo 的内容确认上下文已更新。然后将上下文保存并持久化到磁盘(通过记录和查询 SQLite db 确认)。

此时,我可以编辑我的任何 Person 对象,所有实体都可以修改、添加、删除等,并且所有更改都通过NSManagedObjectContextObjectsDidChangeNotification 确认更改上下文并确认通过持久化到磁盘记录和查询 SQLite - 一切正常。

但是,重新启动应用后,“职业”和“描述”不会保留。它们没有设置为transient(但是它们是“可选的”),并且在设置后会保存主要上下文(有时会保存几次)。更重要的是,如果我退出应用程序,在再次打开它之前,我可以查询 SQLite 数据库并确认磁盘上仍然存在更改。

重新打开应用程序后,我可以确认磁盘上的所有内容都与我退出时相同。 然而,当我在我的 App Delegate 中初始化 Core Data 时,NSManagedObjectContextObjectsDidChangeNotification 通知我发生了一些变化。由于某种原因,“职业”和“描述”已经消失了。它们没有被设置为 null,它们被设置为长度为零的字符串。因此,下次发生触发保存的事情时,“职业”和“描述”被设置为零长度字符串并消失。这一切都发生在启动时——我不访问视图控制器或任何其他甚至查询这些特定字段的东西。然而,我确实展示了一个视图控制器,它确实需要一个填充一个显示 People 对象的 UITableView 的获取请求,尽管它没有专门显示任何一个有问题的实体。

有一个从 Person 1 到 Person 2 的轻量级核心数据模型迁移,但是,当切换回 Person 1 时,这个问题仍然存在,这让我相信这不是迁移问题。

我正在寻求有关从何处着手解决此问题的建议。我无法发布代码 - 我不知道问题发生在我的应用程序的哪个位置。我试图通过确认上下文中何时发生更改以及与磁盘上的内容相比如何进行故障排除,我只是不知道从哪里开始。我不知道为什么这些实体(而且只有其中一些)正在消失。有人将如何开始解决此类问题?任何帮助表示赞赏。

【问题讨论】:

在您的Person 托管对象模型中,为有问题的属性创建自定义设置器并添加断点。如果这些实际上在您的应用重新启动时被修改了,您应该会通过这些方法看到发生的情况,并且堆栈跟踪会提示您是谁在调用它。 如果您将属性重命名为不同的名称会怎样?尝试occupation1description1 看看问题是否仍然存在,然后从那里开始。我很确定您不应该使用description 作为属性名称,因为它会覆盖NSObject 实现的description。 edit 是的,请参阅此处,文档说不鼓励您覆盖 description,因为结果可能无法预测 developer.apple.com/library/mac/documentation/Cocoa/Conceptual/… 在有问题的实体中,覆盖validateValue:forKey:error,并添加条件代码,当value 为空字符串且key 是麻烦的字段之一时记录。现在,在日志行上放置一个断点,您将能够通过回溯查看到底是谁将该字段设置为空字符串。 【参考方案1】:

感谢@Rog 和@Avi 的指导,我能够为相关属性设置自定义设置器并覆盖validateValue:forKey:error,并在每个设置中设置断点。从这里,我能够看到调用方法并正确诊断问题。

实际问题是我误解了在初始化 Core Data 时为每个对象调用initWithEntity:insertIntoManagedObjectContext:,我的印象是它只会在最初创建对象时调用(一次且仅一次)。有问题的代码位于initWithEntity:insertIntoManagedObjectContext:

感谢您的帮助!

【讨论】:

以上是关于核心数据 - 重新启动应用程序时部分数据丢失的主要内容,如果未能解决你的问题,请参考以下文章

房间数据库在重新启动应用程序时丢失数据

应用程序重新启动时照片丢失并取消固定

MagicalRecord 重新启动应用程序时删除核心数据存储

Heroku:每次测功机重新启动时都会丢失 Django 数据库文件

e:应用重启后核心数据自引用关系丢失

快速的核心数据。应用程序丢失数据?