It seems there are 2 ways to perform asynchronous read in CoreData, without blocking main thread UI.
newBackgroundContext + FetchRequest
Source : https://www.advancedswift.com/core-data-background-fetch-save-create/
// Create a new background managed object context
let context = persistentContainer.newBackgroundContext()
// If needed, ensure the background context stays
// up to date with changes from the parent
context.automaticallyMergesChangesFromParent = true
// Perform operations on the background context
// asynchronously
context.perform {
do {
// Create a fetch request
let fetchRequest: NSFetchRequest<CustomEntity>
fetchRequest = CustomEntity.fetchRequest()
fetchRequest.fetchLimit = 1
let objects = try context.fetch(fetchRequest)
// Handle fetched objects
}
catch let error {
// Handle error
}
}
newBackgroundContext + NSAsynchronousFetchRequest
Source: https://www.marcosantadev.com/coredata_crud_concurrency_swift_2/
let privateManagedObjectContext = persistentContainer.newBackgroundContext()
// Creates a fetch request to get all the dogs saved
let fetchRequest = NSFetchRequest<NSFetchRequestResult>(entityName: "Dog")
// Creates `asynchronousFetchRequest` with the fetch request and the completion closure
let asynchronousFetchRequest = NSAsynchronousFetchRequest(fetchRequest: fetchRequest) { asynchronousFetchResult in
// Retrieves an array of dogs from the fetch result `finalResult`
guard let result = asynchronousFetchResult.finalResult as? [Dog] else { return }
// Dispatches to use the data in the main queue
DispatchQueue.main.async {
// Do something
}
}
do {
// Executes `asynchronousFetchRequest`
try privateManagedObjectContext.execute(asynchronousFetchRequest)
} catch let error {
print("NSAsynchronousFetchRequest error: \(error)")
}
However, note that, the above code will unfortunately cause fatal error, if I were to enable flag -com.apple.CoreData.ConcurrencyDebug 1.
So far, I do not have a good solution to such. For more detail, please refer to https://developer.apple.com/forums/thread/697718 ?
May I know, what is the difference among newBackgroundContext + FetchRequest vs newBackgroundContext + NSAsynchronousFetchRequest? How should I choose one over another? Thank you.