帮助您轻松处理 Core Data 的持久化历史跟踪
使用持久化历史记录跟踪来确定自启用持久化历史记录跟踪以来存储中发生了哪些更改。—— Apple 文档
启用持久化历史记录跟踪后,您的应用程序将开始为 Core Data 存储中发生的任何更改创建事务。无论它们来自应用程序扩展、后台上下文还是主应用程序。
应用程序的每个目标都可以获取自给定日期以来发生的事务,并将它们合并到本地存储中。 这样,您就可以及时了解其他持久化存储协调器所做的更改,并保持存储的最新状态。 合并所有事务后,您可以更新合并日期,以便下次合并时,您只会获得尚未处理的新事务。
持久化历史跟踪套件 将为您自动化上述流程。
收到来自 Core Data 的持久化历史跟踪的远程通知后,持久化历史跟踪套件将执行以下操作
有关其工作原理的更具体细节,请阅读 在 CoreData 中使用持久化历史跟踪 或 Using Persistent History Tracking in CoreData 。
// in Core Data Stack
import PersistentHistoryTrackingKit
init() {
container = NSPersistentContainer(name: "PersistentTrackBlog")
// Prepare your Container
let desc = container.persistentStoreDescriptions.first!
// Turn on persistent history tracking in persistentStoreDescriptions
desc.setOption(true as NSNumber,
forKey: NSPersistentHistoryTrackingKey)
desc.setOption(true as NSNumber,
forKey: NSPersistentStoreRemoteChangeNotificationPostOptionKey)
container.loadPersistentStores(completionHandler: { _, _ in })
container.viewContext.transactionAuthor = "app1"
// after loadPersistentStores
let kit = PersistentHistoryTrackingKit(
container: container,
currentAuthor: "app1",
allAuthors: ["app1", "app2", "app3"],
userDefaults: userDefaults,
logLevel: 3,
)
}
当前应用程序的作者名称。 该名称通常与视图上下文的事务名称相同
container.viewContext.transactionAuthor = "app1"
由持久化历史跟踪套件管理的所有成员的作者名称。
持久化历史跟踪套件应仅用于管理由开发人员创建的应用程序、应用程序扩展和后端上下文生成的事务; 其他系统生成的事务(例如,使用 CloudKit 的 Core Data)由系统本身处理。
例如,如果您的应用程序作者名称为:“appAuthor”,而您的应用程序扩展作者名称为:“extensionAuthor”,那么。
allAuthors: ["appAuthor", "extensionAuthor"],
对于在后端上下文中生成的事务,如果未设置为自动合并,则后端上下文也应具有单独的作者名称。
allAuthors: ["appAuthor", "extensionAuthor", "appBatchAuthor"],
是否合并 Core Data 与 CloudKit 导入的网络数据,仅在需要实时切换 Core Data 云同步状态的场景中使用。 有关使用详情,请参阅 实时切换 Core Data 云同步状态
某些作者(例如用于批量更改的后台上下文)仅创建事务,而不合并和清理其他作者生成的事务。 您可以通过在 batchAuthors 中设置它们来加快此类事务的清理速度。
batchAuthors: ["appBatchAuthor"],
即使未设置,这些事务也会在达到 maximumDuration 后自动清除。
通常,事务仅在被所有作者合并后才会被清除。 但是,在某些情况下,个别作者可能长时间未运行或尚未实施,导致事务保留在 SQLite 中。 从长远来看,这会导致数据库的性能下降。
通过设置 maximumDuration,持久化历史跟踪套件将强制删除已达到设置持续时间的事务。 默认设置为 7 天。
maximumDuration: 60 * 60 * 24 * 7,
对事务执行清理不会损害应用程序的数据。
用于合并事务的上下文,通常是应用程序的视图上下文。 默认情况下,它会自动设置为容器的视图上下文。
contexts: [viewContext],
如果使用了 App Group,请使用该组可用的 UserDefaults。
let appGroupUserDefaults = UserDefaults(suiteName: "group.com.yourGroup")!
userDefaults: appGroupUserDefaults,
持久化历史跟踪套件目前支持三种事务清理策略
none
仅合并,不清理
byDuration
设置清理之间的最短时间间隔
byNotification
设置清理之间的最小通知数
// Each notification is cleaned up
cleanStrategy: .byNotification(times: 1),
// At least 60 seconds between cleanings
cleanStrategy: .byDuration(seconds: 60),
当清理策略设置为 none 时,可以通过生成单独的清理实例在适当的时间执行清理。
let kit = PersistentHistoryTrackingKit(
container: container,
currentAuthor: "app1",
allAuthors: "app1,app2,app3",
userDefaults: userDefaults,
cleanStrategy: .byNotification(times: 1),
logLevel: 3,
autoStart: false
)
let cleaner = kit.cleanerBuilder()
// Execute cleaner at the right time, for example when the application enters the background
clear()
UserDefaults 中时间戳的字符串前缀。
持久化历史跟踪套件提供默认的日志输出。 要通过您正在使用的日志记录系统导出持久化历史跟踪套件信息,只需使您的日志记录代码符合 PersistentHistoryTrackingKitLoggerProtocol 即可。
public protocol PersistentHistoryTrackingKitLoggerProtocol {
func log(type: PersistentHistoryTrackingKitLogType, message: String)
}
struct MyLogger: PersistentHistoryTrackingKitLoggerProtocol {
func log(type: PersistentHistoryTrackingKitLogType, message: String) {
print("[\(type.rawValue.uppercased())] : message")
}
}
logger:MyLogger(),
可以通过设置 logLevel 来控制日志消息的输出
是否在创建持久化历史跟踪套件实例后立即启动它。
在应用程序执行期间,可以通过 start() 或 stop() 更改运行状态。
kit.start()
kit.stop()
.iOS(.v13),
.macOS(.v10_15),
.macCatalyst(.v13),
.tvOS(.v13),
.watchOS(.v6)
dependencies: [
.package(url: "https://github.com/fatbobman/PersistentHistoryTrackingKit.git", from: "1.0.0")
]
本库是在 MIT 许可证下发布的。 有关详细信息,请参阅 LICENSE。