Helps you easily handle Core Data's Persistent History Tracking

Overview

Persistent History Tracking Kit

Helps you easily handle Core Data's Persistent History Tracking

中文版说明

What's This?

Use persistent history tracking to determine what changes have occurred in the store since the enabling of persistent history tracking. —— Apple Documentation

When Persistent History Tracking is enabled, your application will begin creating transactions for any changes that occur in Core Data Storage. Whether they come from application extensions, background contexts, or the main application.

Each target of your application can fetch the transactions that have occurred since a given date and merge them into the local storage. This way, you can keep up to date with changes made by other persistent storage coordinators and keep your storage up to date. After merging all transactions, you can update the merge date so that the next time you merge, you will only get the new transactions that have not yet been processed.

The Persistent History Tracking Kit will automate the above process for you.

How does persistent history tracking work?

Upon receiving a remote notification of Persistent History Tracking from Core Data, Persistent History Tracking Kit will do the following:

  • Query the current author's (current author) last merge transaction time
  • Get new transactions created by other applications, application extensions, background contexts, etc. (all authors) in addition to this application since the date of the last merged transaction
  • Merge the new transaction into the specified context (usually the current application's view context)
  • Update the current application's merge transaction time
  • Clean up transactions that have been merged by all applications

For more specific details on how this works, read 在 CoreData 中使用持久化历史跟踪 or Persistent History Tracking in Core Data .

Usage

// 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,
    )
}

Parameters

currentAuthor

The name of the author of the current application. The name is usually the same as the transaction name of the view context

container.viewContext.transactionAuthor = "app1"

allAuthors

The author name of all members managed by the Persistent History Tracking Kit.

Persistent History Tracking Kit should only be used to manage transactions generated by developer-created applications, application extensions, and backend contexts; other system-generated transactions (e.g. Core Data with CloudKit) are handled by the system itself.

For example, if your application author name is: "appAuthor" and your application extension author name is: "extensionAuthor", then.

allAuthors: ["appAuthor", "extensionAuthor"],

For transactions generated in the backend context, the backend context should also have a separate author name if it is not set to auto-merge.

allAuthors: ["appAuthor", "extensionAuthor", "appBatchAuthor"],

batchAuthors

Some authors (such as background contexts for batch changes) only create transactions and do not merge and clean up transactions generated by other authors. You can speed up the cleanup of such transactions by setting them in batchAuthors.

batchAuthors: ["appBatchAuthor"],

Even if not set, these transactions will be automatically cleared after reaching maximumDuration.

maximumDuration

Normally, transactions are only cleaned up after they have been merged by all authors. However, in some cases, individual authors may not run for a long time or may not be implemented yet, causing transactions to remain in SQLite. In the long run, this can cause a performance degradation of the database.

By setting maximumDuration, Persistent History Tracking Kit will force the removal of transactions that have reached the set duration. The default setting is 7 days.

maximumDuration: 60 * 60 * 24 * 7,

Performing cleanup on transactions does not harm the application's data.

contexts

The context used for merging transactions, usually the application's view context. By default, it is automatically set to the container's view context.

contexts: [viewContext],

userDefaults

If an App Group is used, use the UserDefaults available for the group.

let appGroupUserDefaults = UserDefaults(suiteName: "group.com.yourGroup")!

userDefaults: appGroupUserDefaults,

cleanStrategy

Persistent History Tracking Kit currently supports three transaction cleanup strategies:

  • none

    Merge only, no cleanup

  • byDuration

    Set a minimum time interval between cleanups

  • byNotification

    Set the minimum number of notifications between cleanups

// Each notification is cleaned up
cleanStrategy: .byNotification(times: 1),
// At least 60 seconds between cleanings
cleanStrategy: .byDuration(seconds: 60),

When the cleanup policy is set to none, cleanup can be performed at the right time by generating separate cleanup instances.

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()

uniqueString

The string prefix for the timestamp in UserDefaults.

logger

The Persistent History Tracking Kit provides default logging output. To export Persistent History Tracking Kit information through the logging system you are using, simply make your logging code conform to the 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

The output of log messages can be controlled by setting logLevel:

  • 0 Turn off log output
  • 1 Important status only
  • 2 Detail information

autoStart

Whether to start the Persistent History Tracking Kit instance as soon as it is created.

During the execution of the application, the running state can be changed by start() or stop().

kit.start()
kit.stop()

Requirements

.iOS(.v13),

.macOS(.v10_15),

.macCatalyst(.v13),

.tvOS(.v13),

.watchOS(.v6)

Install

dependencies: [
  .package(url: "https://github.com/fatbobman/PersistentHistoryTrackingKit.git", from: "1.0.0")
]

License

This library is released under the MIT license. See LICENSE for details.

You might also like...
A minimalistic, thread safe, non-boilerplate and super easy to use version of Active Record on Core Data.
A minimalistic, thread safe, non-boilerplate and super easy to use version of Active Record on Core Data.

Skopelos A minimalistic, thread-safe, non-boilerplate and super easy to use version of Active Record on Core Data. Simply all you need for doing Core

HitList is a Swift App shows the implementation of Core Data.
HitList is a Swift App shows the implementation of Core Data.

HitList HitList is a Swift App shows the implementation of Core Data. It is the demo app of Ray Wenderlich's tech blog. For details please reference G

A synchronization framework for Core Data.

Core Data Ensembles Author: Drew McCormack Created: 29th September, 2013 Last Updated: 15th February, 2017 Ensembles 2 is now available for purchase a

Core Data code generation

mogenerator Visit the project's pretty homepage. Here's mogenerator's elevator pitch: mogenerator is a command-line tool that, given an .xcdatamodel f

Super Awesome Easy Fetching for Core Data!

MagicalRecord In software engineering, the active record pattern is a design pattern found in software that stores its data in relational databases. I

A type-safe, fluent Swift library for working with Core Data
A type-safe, fluent Swift library for working with Core Data

Core Data Query Interface (CDQI) is a type-safe, fluent, intuitive library for working with Core Data in Swift. CDQI tremendously reduces the amount o

A feature-light wrapper around Core Data that simplifies common database operations.
A feature-light wrapper around Core Data that simplifies common database operations.

Introduction Core Data Dandy is a feature-light wrapper around Core Data that simplifies common database operations. Feature summary Initializes and m

The Big Nerd Ranch Core Data Stack
The Big Nerd Ranch Core Data Stack

BNR Core Data Stack The BNR Core Data Stack is a small Swift framework that makes it both easier and safer to use Core Data. A better fetched results

100% Swift Simple Boilerplate Free Core Data Stack. NSPersistentContainer
100% Swift Simple Boilerplate Free Core Data Stack. NSPersistentContainer

DATAStack helps you to alleviate the Core Data boilerplate. Now you can go to your AppDelegate remove all the Core Data related code and replace it wi

Comments
  • 单元测试失败

    单元测试失败

    CleanShot 2022-10-25 at 19 13 35

    我在尝试使用NSPersistentHistoryToken方式来记录上一次位置(还是觉得Date()可能不够准确,一个错误的时间是否会导致用户永远不会同步或被直接删除数据),不过我下午才通过您的文章学习PersistentHistory,了解很少。想借助您的单元测试验证,但是现在单元测试通过不了,麻烦看看能否抽出时间修复一下,谢谢。

    借鉴Apple的代码如下: https://github.com/hstdt/AppleSamples/blob/d66a7ad5a4c8bb1d8bfd265c597ed6d2bf2c3ae4/SynchronizingALocalStoreToTheCloud/CoreDataCloudKitDemo/DataProvider/CoreDataStack.swift#L103-L134

    opened by hstdt 37
Releases(1.0.5)
Owner
东坡肘子
家庭煮夫.专业带娃. 微信公共号: 肘子的Swift记事本
东坡肘子
Core Data Generator (CDG for short) is a framework for generation (using Sourcery) of Core Data entities from plain structs/classes/enums.

Core Data Generator Introduction Features Supported platforms Installation CDG Setup RepositoryType ModelType DataStoreVersion MigrationPolicy Basic U

Lotusflare 18 Sep 19, 2022
A Swift framework that wraps CoreData, hides context complexity, and helps facilitate best practices.

Cadmium is a Core Data framework for Swift that enforces best practices and raises exceptions for common Core Data pitfalls exactly where you make the

Jason Fieldman 123 Oct 18, 2022
A Swift framework that wraps CoreData, hides context complexity, and helps facilitate best practices.

Cadmium is a Core Data framework for Swift that enforces best practices and raises exceptions for common Core Data pitfalls exactly where you make them.

Jason Fieldman 123 Oct 18, 2022
Super awesome Swift minion for Core Data (iOS, macOS, tvOS)

⚠️ Since this repository is going to be archived soon, I suggest migrating to NSPersistentContainer instead (available since iOS 10). For other conven

Marko Tadić 306 Sep 23, 2022
A powerful and elegant Core Data framework for Swift.

A powerful and elegant Core Data framework for Swift. Usage Beta version. New docs soon... Simple do that: let query = persistentContainer.viewContext

null 782 Nov 6, 2022
CloudCore is a framework that manages syncing between iCloud (CloudKit) and Core Data written on native Swift.

CloudCore CloudCore is a framework that manages syncing between iCloud (CloudKit) and Core Data written on native Swift. Features Leveraging NSPersist

deeje cooley 123 Dec 31, 2022
Unleashing the real power of Core Data with the elegance and safety of Swift

Unleashing the real power of Core Data with the elegance and safety of Swift Dependency managers Contact Swift 5.4: iOS 11+ / macOS 10.13+ / watchOS 4

John Estropia 3.7k Jan 9, 2023
JSQCoreDataKit - A swifter Core Data stack

JSQCoreDataKit A swifter Core Data stack About This library aims to do the following: Encode Core Data best practices, so you don't have to think "is

Jesse Squires 596 Dec 3, 2022
JustPersist is the easiest and safest way to do persistence on iOS with Core Data support out of the box.

JustPersist JustPersist is the easiest and safest way to do persistence on iOS with Core Data support out of the box. It also allows you to migrate to

Just Eat 167 Mar 13, 2022
QueryKit, a simple type-safe Core Data query language.

QueryKit QueryKit, a simple type-safe Core Data query language. Usage QuerySet<Person>(context, "Person")

QueryKit 1.5k Dec 20, 2022