Since unique constraint is not something available when using CloudKit and storing some entities inside NSPersistentCloudKitContainer
would cause duplicated records after the data is synced across multiple devices.
Is there any existing best practice to deduplicate Core Data entity records stored on CloudKit?
I store the app's current user object in Core Data with iCloud user record ID as the unique identifier; however, after the entry got synced to other devices, multiple users appear under the User
SQLite data.
func getLocalUser() -> User? {
/// Try to fetch the only local user
let idMixpanel = DCMixpanel.shared.distinctId
let fetchRequest: NSFetchRequest<User> = User.fetchRequest()
let userPredicate = NSPredicate(
format: "%K = %@",
#keyPath(User.idMixpanel),
idMixpanel
)
fetchRequest.predicate = userPredicate
let userList = try? container.viewContext.fetch(fetchRequest)
if let user = userList?.first {
if user.idCloudKit == nil {
/// This method is async and the ID is not available immediately after function invocation
setupCloudKitUserID()
}
return user
}
/// Create a new local user if no user found with local ID
let userLocalNew = User(context: container.viewContext)
userLocalNew.idMixpanel = DCMixpanel.shared.distinctId
saveContext()
return userLocalNew
}
My solution is to create a mergeLocalUser
method:
private func mergeLocalUser() -> User? {
/// (1) Fetch all users
/// (2) Merge users if there are more than one user in the local database
/// (3) Implement custom user properties merging logic
/// (4) Delete all user instances and re-create a new user
return newUserInstance
}