SlideShare ist ein Scribd-Unternehmen logo
1 von 32
Downloaden Sie, um offline zu lesen
Core Data with Swift 3
Capital One Engineering Tech Talks
Korhan Bircan
Senior Engineering Manager, Capital One
Roadmap
• Persistent Store Types
• What is Core Data?
• Demos
• App Architecture
• Core Data setup and common operations
• Concurrency
• Migration
• Faults and Failures
• Core Data vs Realm
Persistent Store Types
Store type Speed Object graph
in memory
Other
XML Slow Whole Externally
parsableBinary Fast Whole N/A
SQLite Fast Partial N/A
In-memory Fast Whole No storage required
What Is Core Data?
• Framework that helps manage the object life
cycle and object graph management, including
persistence
• Grouping, filtering, and organization of data
• Change tracking
• Lazy loading of objects
• User interface synchronization
Demo - No Persistence
Demo - Core Data
Demo - Realm
LoginViewController
TimelineDataSourceSession TimelineViewController
Twitter
TimelineResponseMapper
App Architecture
LoginViewController
TimelineDataSourceSession TimelineViewController
CoreDataStack
Twitter
TimelineResponseMapper
App Architecture
Core Data Stack
Diagram courtesy of Apple
• Entity, attribute
• Managed Object, Managed Object Context
• Managed Object Model
• Persistent Store: NSQLiteStoreType (non-atomic), NSXMLStoreType (macOS,
atomic), NSBinaryStoreType (atomic), NSInMemoryStoreType (atomic),
NSIncrementalStore (JSON, CSV?)
• Persistent Store Coordinator
• Relationships
• Fetch Request, Predicate, Sort Descriptor
• Fetched Results Controller
Core Data Stack
• Persistent Store Container
Setup (Swift 2.3)
lazy var applicationDocumentsDirectory: NSURL = {
// The directory the application uses to store the Core Data store file. This code uses a directory named "CapitalOne.Delete" in the application's documents Application Support directory.
let urls = NSFileManager.defaultManager().URLsForDirectory(.DocumentDirectory, inDomains: .UserDomainMask)
return urls[urls.count-1]
}()
lazy var managedObjectModel: NSManagedObjectModel = {
// The managed object model for the application. This property is not optional. It is a fatal error for the application not to be able to find and load its model.
let modelURL = NSBundle.mainBundle().URLForResource("Delete", withExtension: "momd")!
return NSManagedObjectModel(contentsOfURL: modelURL)!
}()
lazy var persistentStoreCoordinator: NSPersistentStoreCoordinator = {
// The persistent store coordinator for the application. This implementation creates and returns a coordinator, having added the store for the application to it. This property is optional
since there are legitimate error conditions that could cause the creation of the store to fail.
// Create the coordinator and store
let coordinator = NSPersistentStoreCoordinator(managedObjectModel: self.managedObjectModel)
let url = self.applicationDocumentsDirectory.URLByAppendingPathComponent("SingleViewCoreData.sqlite")
var failureReason = "There was an error creating or loading the application's saved data."
do {
try coordinator.addPersistentStoreWithType(NSSQLiteStoreType, configuration: nil, URL: url, options: nil)
} catch {
// Report any error we got.
var dict = [String: AnyObject]()
dict[NSLocalizedDescriptionKey] = "Failed to initialize the application's saved data"
dict[NSLocalizedFailureReasonErrorKey] = failureReason
dict[NSUnderlyingErrorKey] = error as NSError
let wrappedError = NSError(domain: "YOUR_ERROR_DOMAIN", code: 9999, userInfo: dict)
// Replace this with code to handle the error appropriately.
// abort() causes the application to generate a crash log and terminate. You should not use this function in a shipping application, although it may be useful during development.
NSLog("Unresolved error (wrappedError), (wrappedError.userInfo)")
abort()
}
return coordinator
}()
lazy var managedObjectContext: NSManagedObjectContext = {
// Returns the managed object context for the application (which is already bound to the persistent store coordinator for the application.) This property is optional since there are
legitimate error conditions that could cause the creation of the context to fail.
let coordinator = self.persistentStoreCoordinator
var managedObjectContext = NSManagedObjectContext(concurrencyType: .MainQueueConcurrencyType)
managedObjectContext.persistentStoreCoordinator = coordinator
return managedObjectContext
}()
// MARK: - Core Data Saving support
func saveContext () {
if managedObjectContext.hasChanges {
do {
try managedObjectContext.save()
} catch {
// Replace this implementation with code to handle the error appropriately.
// abort() causes the application to generate a crash log and terminate. You should not use this function in a shipping application, although it may be useful during development.
let nserror = error as NSError
NSLog("Unresolved error (nserror), (nserror.userInfo)")
abort()
}
}
}
Setup (Swift 3)
lazy var managedContext: NSManagedObjectContext = {
let context = self.storeContainer.viewContext
context.mergePolicy = NSMergeByPropertyObjectTrumpMergePolicy
return context
}()
lazy var storeContainer: NSPersistentContainer = {
let container = NSPersistentContainer(name: self.modelName)
container.loadPersistentStores { (storeDescription, error) in
if let error = error as NSError? {
print("Unresolved error (error), (error.userInfo)")
} else {
print("Persistent store location: (storeDescription.url?.absoluteString)")
}
}
return container
}()
func saveContext () {
guard managedContext.hasChanges else {
return
}
do {
try self.managedContext.save()
} catch let error as NSError {
print("Unresolved error (error), (error.userInfo)")
}
}
Modeling Data
Saving and Retrieving Objects
Save
let tweet = Tweet(context: context)
try! managedObjectContext.save()
Retrieve
let request: NSFetchRequest<Tweet> = Tweet.fetchRequest()
let allTweets = try! context.fetch(request)
Delete
try! managedObjectContext.delete(tweet)
try! managedObjectContext.save()
Filter
let fetchRequest = Tweet.fetchRequest()
fetchRequest.predicate = NSPredicate(format: "text contains[c]
%@", keyword)
fetchRequest.sortDescriptors = [NSSortDescriptor(key:
#keyPath(Tweet.createdAt), ascending: false)]
try! fetchedResultsController?.performFetch()
Fetch Predicates
class Person: NSObject {
let firstName: String
let lastName: String
let age: Int
}
let bobPredicate = NSPredicate(format: "firstName = 'Bob'")
// let smithPredicate = NSPredicate(format: "lastName = %@", "Smith")
// let thirtiesPredicate = NSPredicate(format: "age >= 30")
fetchRequest.predicate = bobPredicate
try! fetchedResultsController?.performFetch()
• Basic Comparisons
=, ==; >=, =>; <=, =<; >; <; !=
• Compound Predicates
AND, &&; OR, ||; NOT, !
• String Comparisons
BEGINSWITH; CONTAINS; ENDSWITH; LIKE; MATCHES
Fetched Results Controller
let fetchRequest.predicate = keyword.isEmpty ? nil : NSPredicate(format: "text contains[c] %@",
keyword)
fetchRequest.sortDescriptors = [NSSortDescriptor(key: #keyPath(Tweet.createdAt), ascending: false)]
let fetchedResultsController = NSFetchedResultsController(fetchRequest: fetchRequest,
managedObjectContext: CoreDataStack.sharedInstance.managedContext,
sectionNameKeyPath: nil,
cacheName: nil)
do {
try fetchedResultsController?.performFetch()
} catch let error as NSError {
print("Fetching error: (error), (error.userInfo)")
}
Wiring Model to UI
override func numberOfSections(in tableView: UITableView) -> Int {
return fetchedResultsController.sections
}
override func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return fetchedResultsController.sections?[section].numberOfObjects
}
override func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) ->
UITableViewCell {
let cell = tableView.dequeueReusableCell(withIdentifier: TweetCell.identifier, for: indexPath)
if let tweet = fetchedResultsController.object(at: indexPath) {
TimelineViewCellAdapter.configure(cell as? TweetCell, tweet: tweet)
}
return cell
}
override func tableView(_ tableView: UITableView, titleForHeaderInSection section: Int) -> String? {
let sectionInfo = fetchedResultsController.sections[section]
return sectionInfo?.name
}
Communicating Data Changes
func controllerWillChangeContent(controller: NSFetchedResultsController) {
tableView.beginUpdates()
}
func controller(controller: NSFetchedResultsController, didChangeSection sectionInfo:
NSFetchedResultsSectionInfo, atIndex sectionIndex: Int, forChangeType type: NSFetchedResultsChangeType) {
switch type {
case .Insert:
tableView.insertSections(NSIndexSet(index: sectionIndex), withRowAnimation: .Fade)
case .Delete:
tableView.deleteSections(NSIndexSet(index: sectionIndex), withRowAnimation: .Fade)
case .Move:
break
case .Update:
break
}
}
func controller(controller: NSFetchedResultsController, didChangeObject anObject: AnyObject, atIndexPath
indexPath: NSIndexPath?, forChangeType type: NSFetchedResultsChangeType, newIndexPath: NSIndexPath?) {
switch type {
case .Insert:
tableView.insertRowsAtIndexPaths([newIndexPath!], withRowAnimation: .Fade)
case .Delete:
tableView.deleteRowsAtIndexPaths([indexPath!], withRowAnimation: .Fade)
case .Update:
configureCell(tableView.cellForRowAtIndexPath(indexPath!)!, indexPath: indexPath!)
case .Move:
tableView.moveRowAtIndexPath(indexPath!, toIndexPath: newIndexPath!)
}
}
func controllerDidChangeContent(controller: NSFetchedResultsController) {
tableView.endUpdates()
}
Concurrency
let jsonArray = … //JSON data to be imported into Core Data
let moc = … //Our primary context on the main queue
let privateMOC =
NSManagedObjectContext(concurrencyType: .PrivateQueueConcurrencyType)
privateMOC.parentContext = moc
privateMOC.performBlock {
for jsonObject in jsonArray {
let mo = … //Managed object that matches the incoming JSON structure
//update managed object with data from the dictionary
}
do {
try privateMOC.save()
moc.performBlockAndWait {
do {
try moc.save()
} catch {
fatalError("Failure to save context: (error)")
}
}
} catch {
fatalError("Failure to save context: (error)")
}
}
Xcode 8 madness
Swift 2.3 vs Swift 3
dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), {
do {
let json = try NSJSONSerialization.JSONObjectWithData(data!, options: [])
TimelineResponseMapper.parseResponse(json)
dispatch_async(dispatch_get_main_queue(), {
self.tableView.reloadData()
})
} catch let jsonError as NSError {
print("json error: (jsonError.localizedDescription)")
}
})
// vs
DispatchQueue.global(qos: DispatchQoS.QoSClass.default).async {
do {
let json = try JSONSerialization.jsonObject(with: data!, options: [])
TimelineResponseMapper.parseResponse(json)
DispatchQueue.main.async {
self.tableView.reloadData()
}
} catch let jsonError as NSError {
print("json error: (jsonError.localizedDescription)")
}
}
Tidbits
• Multiple managed object contexts
• Migration
• Faulting and uniquing
• Concurrency failures
Migration
lazy var storeContainer: NSPersistentContainer = {
let container = NSPersistentContainer(name: self.modelName)
container.loadPersistentStores { (storeDescription, error) in
storeDescription.shouldMigrateStoreAutomatically = true
storeDescription.shouldInferMappingModelAutomatically = true
Why faults?
• Dictionary definition:
1. (noun) an unattractive or unsatisfactory feature, esp. in a piece of
work or in a person’s character.
2. (noun) responsibility for an accident or misfortune.
3. (noun) an extended break in a body of rock, marked by the
relative displacement and discontinuity of strata on either side of a
particular surface.
• Apple’s definition:
• A fault is a placeholder object that represents a managed object that
has not yet been fully realized, or a collection object that represents
a relationship.
Why faults?
Diagram courtesy of Apple
Why Faults May Fail
2016-10-11 22:20:24.530 CoreDataTest[24222:60b] * Assertion failure in
-[AppDelegate save], .../AppDelegate.swift:28 2016-10-11 22:20:24.530
CoreDataTest[24222:60b] * Terminating app due to uncaught exception
'NSInternalInconsistencyException', reason: 'Save failed {type =
immutable dict, count = 2, entries => 1 : {contents =
"NSAffectedObjectsErrorKey"} = ( " (entity: Tweet; id: 0x6b8bf10 ;
data: )" ) 2 : {contents = "NSUnderlyingException"} = CoreData could
not fulfill a fault for '0x6b8bf10 ' }
Handling Fault Failures
• managedObjectContext.shouldDeleteInaccessibleFaults
• Prefetch everything
• Write lots of code (existingobjectwithId() to
make sure the object is in the database before
referencing it)
• Use query generators
Concurrency Failures
let firstTweet = Tweet(context: managedContext)
// Synchronously performs the block on the context's queue.
//May safely be called reentrantly.
managedContext.performAndWait {
do {
firstTweet.text = "Something interesting happened today..."
try self.managedContext.save()
} catch let error as NSError {
print("Unresolved error (error), (error.userInfo)")
}
}
managedContext2.performAndWait {
let text = firstTweet.text
print(text)
}
2016-10-11 22:20:24.530 CoreDataTest[24222:60b]
CoreData concurrency failure
Realm
CoreData Realm
Save
let tweet = Tweet(context: context)
try! managedObjectContext.save()
let realm = try! Realm()
let tweet = Tweet()
try! realm.write {
realm.add(tweet)
}
Retrieve
let request: NSFetchRequest<Tweet> =
Tweet.fetchRequest()
let allTweets = try! context.fetch(request)
let tweets = realm.objects(Tweet.self)
Delete
try! managedObjectContext.delete(tweet)
try! managedObjectContext.save()
try! realm.write {
realm.delete(tweet)
}
Filter
let fetchRequest = Tweet.fetchRequest()
fetchRequest.predicate = NSPredicate(format: "text contains[c] %@",
keyword)
fetchRequest.sortDescriptors = [NSSortDescriptor(key:
#keyPath(Tweet.createdAt), ascending: false)]
try! fetchedResultsController?.performFetch()
let predicate = NSPredicate(format: "text contains[c] %@", keyword)
let tweets = realm.objects(Tweet.self).filter(predicate)
let sortedTweets = tweets.sorted("createdAt", ascending: ascending)
Core Data vs Realm
Core Data Realm
Latest Swift compatibility
Future proof
Ease of use
Multithreading
Speed
Encryption
Support
Real life testing
Next Time
• Persisting Data in the Cloud

Weitere ähnliche Inhalte

Was ist angesagt?

Hibernate Tutorial
Hibernate TutorialHibernate Tutorial
Hibernate TutorialRam132
 
Entity Framework Database and Code First
Entity Framework Database and Code FirstEntity Framework Database and Code First
Entity Framework Database and Code FirstJames Johnson
 
Ch06 ado.net fundamentals
Ch06 ado.net fundamentalsCh06 ado.net fundamentals
Ch06 ado.net fundamentalsMadhuri Kavade
 
Introduction To Hibernate
Introduction To HibernateIntroduction To Hibernate
Introduction To Hibernateashishkulkarni
 
ASP.NET Session 11 12
ASP.NET Session 11 12ASP.NET Session 11 12
ASP.NET Session 11 12Sisir Ghosh
 
Data Binding and Data Grid View Classes
Data Binding and Data Grid View ClassesData Binding and Data Grid View Classes
Data Binding and Data Grid View ClassesArvind Krishnaa
 
For Beginners - Ado.net
For Beginners - Ado.netFor Beginners - Ado.net
For Beginners - Ado.netTarun Jain
 
Chapter 3: ado.net
Chapter 3: ado.netChapter 3: ado.net
Chapter 3: ado.netNgeam Soly
 
Entity Framework: Code First and Magic Unicorns
Entity Framework: Code First and Magic UnicornsEntity Framework: Code First and Magic Unicorns
Entity Framework: Code First and Magic UnicornsRichie Rump
 
ASP.NET 08 - Data Binding And Representation
ASP.NET 08 - Data Binding And RepresentationASP.NET 08 - Data Binding And Representation
ASP.NET 08 - Data Binding And RepresentationRandy Connolly
 
[2015/2016] Local data storage for web-based mobile apps
[2015/2016] Local data storage for web-based mobile apps[2015/2016] Local data storage for web-based mobile apps
[2015/2016] Local data storage for web-based mobile appsIvano Malavolta
 

Was ist angesagt? (19)

Hibernate Tutorial
Hibernate TutorialHibernate Tutorial
Hibernate Tutorial
 
Ch 7 data binding
Ch 7 data bindingCh 7 data binding
Ch 7 data binding
 
Entity Framework Database and Code First
Entity Framework Database and Code FirstEntity Framework Database and Code First
Entity Framework Database and Code First
 
Ch06 ado.net fundamentals
Ch06 ado.net fundamentalsCh06 ado.net fundamentals
Ch06 ado.net fundamentals
 
For Beginers - ADO.Net
For Beginers - ADO.NetFor Beginers - ADO.Net
For Beginers - ADO.Net
 
Introduction To Hibernate
Introduction To HibernateIntroduction To Hibernate
Introduction To Hibernate
 
ASP.NET Session 11 12
ASP.NET Session 11 12ASP.NET Session 11 12
ASP.NET Session 11 12
 
ADO.NET
ADO.NETADO.NET
ADO.NET
 
Data Binding and Data Grid View Classes
Data Binding and Data Grid View ClassesData Binding and Data Grid View Classes
Data Binding and Data Grid View Classes
 
Ado .net
Ado .netAdo .net
Ado .net
 
ADO.NET
ADO.NETADO.NET
ADO.NET
 
For Beginners - Ado.net
For Beginners - Ado.netFor Beginners - Ado.net
For Beginners - Ado.net
 
Chapter 3: ado.net
Chapter 3: ado.netChapter 3: ado.net
Chapter 3: ado.net
 
Entity Framework: Code First and Magic Unicorns
Entity Framework: Code First and Magic UnicornsEntity Framework: Code First and Magic Unicorns
Entity Framework: Code First and Magic Unicorns
 
Ado.Net Tutorial
Ado.Net TutorialAdo.Net Tutorial
Ado.Net Tutorial
 
ADO .Net
ADO .Net ADO .Net
ADO .Net
 
ASP.NET 08 - Data Binding And Representation
ASP.NET 08 - Data Binding And RepresentationASP.NET 08 - Data Binding And Representation
ASP.NET 08 - Data Binding And Representation
 
ReactJS
ReactJSReactJS
ReactJS
 
[2015/2016] Local data storage for web-based mobile apps
[2015/2016] Local data storage for web-based mobile apps[2015/2016] Local data storage for web-based mobile apps
[2015/2016] Local data storage for web-based mobile apps
 

Andere mochten auch

ios_summit_2016_korhan
ios_summit_2016_korhanios_summit_2016_korhan
ios_summit_2016_korhanKorhan Bircan
 
Useful Tools for Making Video Games - XNA (2008)
Useful Tools for Making Video Games - XNA (2008)Useful Tools for Making Video Games - XNA (2008)
Useful Tools for Making Video Games - XNA (2008)Korhan Bircan
 
Встреча №8. NSIncrementalStore, или как заставить Core Data варить ваш собств...
Встреча №8. NSIncrementalStore, или как заставить Core Data варить ваш собств...Встреча №8. NSIncrementalStore, или как заставить Core Data варить ваш собств...
Встреча №8. NSIncrementalStore, или как заставить Core Data варить ваш собств...CocoaHeads
 
Background Audio Playback
Background Audio PlaybackBackground Audio Playback
Background Audio PlaybackKorhan Bircan
 
Useful Tools for Making Video Games - fmod (2008)
Useful Tools for Making Video Games - fmod (2008)Useful Tools for Making Video Games - fmod (2008)
Useful Tools for Making Video Games - fmod (2008)Korhan Bircan
 
Next-Gen shaders (2008)
Next-Gen shaders (2008)Next-Gen shaders (2008)
Next-Gen shaders (2008)Korhan Bircan
 
Core Data presentation
Core Data presentationCore Data presentation
Core Data presentationjoaopmaia
 
Advanced Imaging on iOS
Advanced Imaging on iOSAdvanced Imaging on iOS
Advanced Imaging on iOSrsebbe
 
Password Cracking with Rainbow Tables
Password Cracking with Rainbow TablesPassword Cracking with Rainbow Tables
Password Cracking with Rainbow TablesKorhan Bircan
 
Swift Bengaluru Meetup slides
Swift Bengaluru Meetup slidesSwift Bengaluru Meetup slides
Swift Bengaluru Meetup slidesPushkar Kulkarni
 
Intro to Core Data
Intro to Core DataIntro to Core Data
Intro to Core DataMake School
 
Client Server Security with Flask and iOS
Client Server Security with Flask and iOSClient Server Security with Flask and iOS
Client Server Security with Flask and iOSMake School
 
Localization and Accessibility on iOS
Localization and Accessibility on iOSLocalization and Accessibility on iOS
Localization and Accessibility on iOSMake School
 
Error Handling in Swift
Error Handling in SwiftError Handling in Swift
Error Handling in SwiftMake School
 
Layout with Stack View, Table View, and Collection View
Layout with Stack View, Table View, and Collection ViewLayout with Stack View, Table View, and Collection View
Layout with Stack View, Table View, and Collection ViewMake School
 
Improving apps with iOS 10 notifications (do iOS 2016)
Improving apps with iOS 10 notifications (do iOS 2016)Improving apps with iOS 10 notifications (do iOS 2016)
Improving apps with iOS 10 notifications (do iOS 2016)Donny Wals
 
WWDC 2016
WWDC 2016WWDC 2016
WWDC 2016PiXeL16
 

Andere mochten auch (20)

ios_summit_2016_korhan
ios_summit_2016_korhanios_summit_2016_korhan
ios_summit_2016_korhan
 
Korhan bircan
Korhan bircanKorhan bircan
Korhan bircan
 
Useful Tools for Making Video Games - XNA (2008)
Useful Tools for Making Video Games - XNA (2008)Useful Tools for Making Video Games - XNA (2008)
Useful Tools for Making Video Games - XNA (2008)
 
Встреча №8. NSIncrementalStore, или как заставить Core Data варить ваш собств...
Встреча №8. NSIncrementalStore, или как заставить Core Data варить ваш собств...Встреча №8. NSIncrementalStore, или как заставить Core Data варить ваш собств...
Встреча №8. NSIncrementalStore, или как заставить Core Data варить ваш собств...
 
Background Audio Playback
Background Audio PlaybackBackground Audio Playback
Background Audio Playback
 
Useful Tools for Making Video Games - fmod (2008)
Useful Tools for Making Video Games - fmod (2008)Useful Tools for Making Video Games - fmod (2008)
Useful Tools for Making Video Games - fmod (2008)
 
Next-Gen shaders (2008)
Next-Gen shaders (2008)Next-Gen shaders (2008)
Next-Gen shaders (2008)
 
Core Data presentation
Core Data presentationCore Data presentation
Core Data presentation
 
Advanced Imaging on iOS
Advanced Imaging on iOSAdvanced Imaging on iOS
Advanced Imaging on iOS
 
Password Cracking with Rainbow Tables
Password Cracking with Rainbow TablesPassword Cracking with Rainbow Tables
Password Cracking with Rainbow Tables
 
Swift Bengaluru Meetup slides
Swift Bengaluru Meetup slidesSwift Bengaluru Meetup slides
Swift Bengaluru Meetup slides
 
SWIFT 3
SWIFT 3SWIFT 3
SWIFT 3
 
Intro to Core Data
Intro to Core DataIntro to Core Data
Intro to Core Data
 
Client Server Security with Flask and iOS
Client Server Security with Flask and iOSClient Server Security with Flask and iOS
Client Server Security with Flask and iOS
 
Localization and Accessibility on iOS
Localization and Accessibility on iOSLocalization and Accessibility on iOS
Localization and Accessibility on iOS
 
Error Handling in Swift
Error Handling in SwiftError Handling in Swift
Error Handling in Swift
 
Layout with Stack View, Table View, and Collection View
Layout with Stack View, Table View, and Collection ViewLayout with Stack View, Table View, and Collection View
Layout with Stack View, Table View, and Collection View
 
What's new in Swift 3
What's new in Swift 3What's new in Swift 3
What's new in Swift 3
 
Improving apps with iOS 10 notifications (do iOS 2016)
Improving apps with iOS 10 notifications (do iOS 2016)Improving apps with iOS 10 notifications (do iOS 2016)
Improving apps with iOS 10 notifications (do iOS 2016)
 
WWDC 2016
WWDC 2016WWDC 2016
WWDC 2016
 

Ähnlich wie Core Data with Swift 3.0

Core data orlando i os dev group
Core data   orlando i os dev groupCore data   orlando i os dev group
Core data orlando i os dev groupAndrew Kozlik
 
Core Data with multiple managed object contexts
Core Data with multiple managed object contextsCore Data with multiple managed object contexts
Core Data with multiple managed object contextsMatthew Morey
 
Understanding backbonejs
Understanding backbonejsUnderstanding backbonejs
Understanding backbonejsNick Lee
 
Introduction to Spring MVC
Introduction to Spring MVCIntroduction to Spring MVC
Introduction to Spring MVCRichard Paul
 
MobileCity:Core Data
MobileCity:Core DataMobileCity:Core Data
MobileCity:Core DataAllan Davis
 
iOSDevCamp 2011 Core Data
iOSDevCamp 2011 Core DataiOSDevCamp 2011 Core Data
iOSDevCamp 2011 Core DataChris Mar
 
Backbone.js — Introduction to client-side JavaScript MVC
Backbone.js — Introduction to client-side JavaScript MVCBackbone.js — Introduction to client-side JavaScript MVC
Backbone.js — Introduction to client-side JavaScript MVCpootsbook
 
Simpler Core Data with RubyMotion
Simpler Core Data with RubyMotionSimpler Core Data with RubyMotion
Simpler Core Data with RubyMotionStefan Haflidason
 
Advance java session 5
Advance java session 5Advance java session 5
Advance java session 5Smita B Kumar
 
Tuning and optimizing webcenter spaces application white paper
Tuning and optimizing webcenter spaces application white paperTuning and optimizing webcenter spaces application white paper
Tuning and optimizing webcenter spaces application white paperVinay Kumar
 
Single Page Applications on JavaScript and ASP.NET MVC4
Single Page Applications on JavaScript and ASP.NET MVC4Single Page Applications on JavaScript and ASP.NET MVC4
Single Page Applications on JavaScript and ASP.NET MVC4Yuriy Shapovalov
 
Local data storage for mobile apps
Local data storage for mobile appsLocal data storage for mobile apps
Local data storage for mobile appsIvano Malavolta
 
Coldbox developer training – session 5
Coldbox developer training – session 5Coldbox developer training – session 5
Coldbox developer training – session 5Billie Berzinskas
 
How to execute an oracle stored procedure with nested table as a parameter fr...
How to execute an oracle stored procedure with nested table as a parameter fr...How to execute an oracle stored procedure with nested table as a parameter fr...
How to execute an oracle stored procedure with nested table as a parameter fr...Priyobroto Ghosh (Mule ESB Certified)
 
Javascript MVC & Backbone Tips & Tricks
Javascript MVC & Backbone Tips & TricksJavascript MVC & Backbone Tips & Tricks
Javascript MVC & Backbone Tips & TricksHjörtur Hilmarsson
 

Ähnlich wie Core Data with Swift 3.0 (20)

Core data orlando i os dev group
Core data   orlando i os dev groupCore data   orlando i os dev group
Core data orlando i os dev group
 
Core Data with multiple managed object contexts
Core Data with multiple managed object contextsCore Data with multiple managed object contexts
Core Data with multiple managed object contexts
 
Understanding backbonejs
Understanding backbonejsUnderstanding backbonejs
Understanding backbonejs
 
Introduction to Spring MVC
Introduction to Spring MVCIntroduction to Spring MVC
Introduction to Spring MVC
 
MobileCity:Core Data
MobileCity:Core DataMobileCity:Core Data
MobileCity:Core Data
 
iOSDevCamp 2011 Core Data
iOSDevCamp 2011 Core DataiOSDevCamp 2011 Core Data
iOSDevCamp 2011 Core Data
 
Backbone.js — Introduction to client-side JavaScript MVC
Backbone.js — Introduction to client-side JavaScript MVCBackbone.js — Introduction to client-side JavaScript MVC
Backbone.js — Introduction to client-side JavaScript MVC
 
Spine.js
Spine.jsSpine.js
Spine.js
 
Backbone js
Backbone jsBackbone js
Backbone js
 
Simpler Core Data with RubyMotion
Simpler Core Data with RubyMotionSimpler Core Data with RubyMotion
Simpler Core Data with RubyMotion
 
70562 (1)
70562 (1)70562 (1)
70562 (1)
 
Advance java session 5
Advance java session 5Advance java session 5
Advance java session 5
 
Intro react js
Intro react jsIntro react js
Intro react js
 
Tuning and optimizing webcenter spaces application white paper
Tuning and optimizing webcenter spaces application white paperTuning and optimizing webcenter spaces application white paper
Tuning and optimizing webcenter spaces application white paper
 
Single Page Applications on JavaScript and ASP.NET MVC4
Single Page Applications on JavaScript and ASP.NET MVC4Single Page Applications on JavaScript and ASP.NET MVC4
Single Page Applications on JavaScript and ASP.NET MVC4
 
Local data storage for mobile apps
Local data storage for mobile appsLocal data storage for mobile apps
Local data storage for mobile apps
 
Coldbox developer training – session 5
Coldbox developer training – session 5Coldbox developer training – session 5
Coldbox developer training – session 5
 
How to execute an oracle stored procedure with nested table as a parameter fr...
How to execute an oracle stored procedure with nested table as a parameter fr...How to execute an oracle stored procedure with nested table as a parameter fr...
How to execute an oracle stored procedure with nested table as a parameter fr...
 
Sqlapi0.1
Sqlapi0.1Sqlapi0.1
Sqlapi0.1
 
Javascript MVC & Backbone Tips & Tricks
Javascript MVC & Backbone Tips & TricksJavascript MVC & Backbone Tips & Tricks
Javascript MVC & Backbone Tips & Tricks
 

Kürzlich hochgeladen

Hostel management system project report..pdf
Hostel management system project report..pdfHostel management system project report..pdf
Hostel management system project report..pdfKamal Acharya
 
Moment Distribution Method For Btech Civil
Moment Distribution Method For Btech CivilMoment Distribution Method For Btech Civil
Moment Distribution Method For Btech CivilVinayVitekari
 
Navigating Complexity: The Role of Trusted Partners and VIAS3D in Dassault Sy...
Navigating Complexity: The Role of Trusted Partners and VIAS3D in Dassault Sy...Navigating Complexity: The Role of Trusted Partners and VIAS3D in Dassault Sy...
Navigating Complexity: The Role of Trusted Partners and VIAS3D in Dassault Sy...Arindam Chakraborty, Ph.D., P.E. (CA, TX)
 
GEAR TRAIN- BASIC CONCEPTS AND WORKING PRINCIPLE
GEAR TRAIN- BASIC CONCEPTS AND WORKING PRINCIPLEGEAR TRAIN- BASIC CONCEPTS AND WORKING PRINCIPLE
GEAR TRAIN- BASIC CONCEPTS AND WORKING PRINCIPLEselvakumar948
 
COST-EFFETIVE and Energy Efficient BUILDINGS ptx
COST-EFFETIVE  and Energy Efficient BUILDINGS ptxCOST-EFFETIVE  and Energy Efficient BUILDINGS ptx
COST-EFFETIVE and Energy Efficient BUILDINGS ptxJIT KUMAR GUPTA
 
Thermal Engineering -unit - III & IV.ppt
Thermal Engineering -unit - III & IV.pptThermal Engineering -unit - III & IV.ppt
Thermal Engineering -unit - III & IV.pptDineshKumar4165
 
Online food ordering system project report.pdf
Online food ordering system project report.pdfOnline food ordering system project report.pdf
Online food ordering system project report.pdfKamal Acharya
 
DC MACHINE-Motoring and generation, Armature circuit equation
DC MACHINE-Motoring and generation, Armature circuit equationDC MACHINE-Motoring and generation, Armature circuit equation
DC MACHINE-Motoring and generation, Armature circuit equationBhangaleSonal
 
Computer Lecture 01.pptxIntroduction to Computers
Computer Lecture 01.pptxIntroduction to ComputersComputer Lecture 01.pptxIntroduction to Computers
Computer Lecture 01.pptxIntroduction to ComputersMairaAshraf6
 
A CASE STUDY ON CERAMIC INDUSTRY OF BANGLADESH.pptx
A CASE STUDY ON CERAMIC INDUSTRY OF BANGLADESH.pptxA CASE STUDY ON CERAMIC INDUSTRY OF BANGLADESH.pptx
A CASE STUDY ON CERAMIC INDUSTRY OF BANGLADESH.pptxmaisarahman1
 
Thermal Engineering-R & A / C - unit - V
Thermal Engineering-R & A / C - unit - VThermal Engineering-R & A / C - unit - V
Thermal Engineering-R & A / C - unit - VDineshKumar4165
 
Engineering Drawing focus on projection of planes
Engineering Drawing focus on projection of planesEngineering Drawing focus on projection of planes
Engineering Drawing focus on projection of planesRAJNEESHKUMAR341697
 
DeepFakes presentation : brief idea of DeepFakes
DeepFakes presentation : brief idea of DeepFakesDeepFakes presentation : brief idea of DeepFakes
DeepFakes presentation : brief idea of DeepFakesMayuraD1
 
Unit 4_Part 1 CSE2001 Exception Handling and Function Template and Class Temp...
Unit 4_Part 1 CSE2001 Exception Handling and Function Template and Class Temp...Unit 4_Part 1 CSE2001 Exception Handling and Function Template and Class Temp...
Unit 4_Part 1 CSE2001 Exception Handling and Function Template and Class Temp...drmkjayanthikannan
 
Wadi Rum luxhotel lodge Analysis case study.pptx
Wadi Rum luxhotel lodge Analysis case study.pptxWadi Rum luxhotel lodge Analysis case study.pptx
Wadi Rum luxhotel lodge Analysis case study.pptxNadaHaitham1
 
Design For Accessibility: Getting it right from the start
Design For Accessibility: Getting it right from the startDesign For Accessibility: Getting it right from the start
Design For Accessibility: Getting it right from the startQuintin Balsdon
 
Online electricity billing project report..pdf
Online electricity billing project report..pdfOnline electricity billing project report..pdf
Online electricity billing project report..pdfKamal Acharya
 

Kürzlich hochgeladen (20)

Hostel management system project report..pdf
Hostel management system project report..pdfHostel management system project report..pdf
Hostel management system project report..pdf
 
Moment Distribution Method For Btech Civil
Moment Distribution Method For Btech CivilMoment Distribution Method For Btech Civil
Moment Distribution Method For Btech Civil
 
Navigating Complexity: The Role of Trusted Partners and VIAS3D in Dassault Sy...
Navigating Complexity: The Role of Trusted Partners and VIAS3D in Dassault Sy...Navigating Complexity: The Role of Trusted Partners and VIAS3D in Dassault Sy...
Navigating Complexity: The Role of Trusted Partners and VIAS3D in Dassault Sy...
 
GEAR TRAIN- BASIC CONCEPTS AND WORKING PRINCIPLE
GEAR TRAIN- BASIC CONCEPTS AND WORKING PRINCIPLEGEAR TRAIN- BASIC CONCEPTS AND WORKING PRINCIPLE
GEAR TRAIN- BASIC CONCEPTS AND WORKING PRINCIPLE
 
COST-EFFETIVE and Energy Efficient BUILDINGS ptx
COST-EFFETIVE  and Energy Efficient BUILDINGS ptxCOST-EFFETIVE  and Energy Efficient BUILDINGS ptx
COST-EFFETIVE and Energy Efficient BUILDINGS ptx
 
Integrated Test Rig For HTFE-25 - Neometrix
Integrated Test Rig For HTFE-25 - NeometrixIntegrated Test Rig For HTFE-25 - Neometrix
Integrated Test Rig For HTFE-25 - Neometrix
 
Thermal Engineering -unit - III & IV.ppt
Thermal Engineering -unit - III & IV.pptThermal Engineering -unit - III & IV.ppt
Thermal Engineering -unit - III & IV.ppt
 
Online food ordering system project report.pdf
Online food ordering system project report.pdfOnline food ordering system project report.pdf
Online food ordering system project report.pdf
 
DC MACHINE-Motoring and generation, Armature circuit equation
DC MACHINE-Motoring and generation, Armature circuit equationDC MACHINE-Motoring and generation, Armature circuit equation
DC MACHINE-Motoring and generation, Armature circuit equation
 
Computer Lecture 01.pptxIntroduction to Computers
Computer Lecture 01.pptxIntroduction to ComputersComputer Lecture 01.pptxIntroduction to Computers
Computer Lecture 01.pptxIntroduction to Computers
 
A CASE STUDY ON CERAMIC INDUSTRY OF BANGLADESH.pptx
A CASE STUDY ON CERAMIC INDUSTRY OF BANGLADESH.pptxA CASE STUDY ON CERAMIC INDUSTRY OF BANGLADESH.pptx
A CASE STUDY ON CERAMIC INDUSTRY OF BANGLADESH.pptx
 
Thermal Engineering-R & A / C - unit - V
Thermal Engineering-R & A / C - unit - VThermal Engineering-R & A / C - unit - V
Thermal Engineering-R & A / C - unit - V
 
Engineering Drawing focus on projection of planes
Engineering Drawing focus on projection of planesEngineering Drawing focus on projection of planes
Engineering Drawing focus on projection of planes
 
DeepFakes presentation : brief idea of DeepFakes
DeepFakes presentation : brief idea of DeepFakesDeepFakes presentation : brief idea of DeepFakes
DeepFakes presentation : brief idea of DeepFakes
 
Unit 4_Part 1 CSE2001 Exception Handling and Function Template and Class Temp...
Unit 4_Part 1 CSE2001 Exception Handling and Function Template and Class Temp...Unit 4_Part 1 CSE2001 Exception Handling and Function Template and Class Temp...
Unit 4_Part 1 CSE2001 Exception Handling and Function Template and Class Temp...
 
Wadi Rum luxhotel lodge Analysis case study.pptx
Wadi Rum luxhotel lodge Analysis case study.pptxWadi Rum luxhotel lodge Analysis case study.pptx
Wadi Rum luxhotel lodge Analysis case study.pptx
 
FEA Based Level 3 Assessment of Deformed Tanks with Fluid Induced Loads
FEA Based Level 3 Assessment of Deformed Tanks with Fluid Induced LoadsFEA Based Level 3 Assessment of Deformed Tanks with Fluid Induced Loads
FEA Based Level 3 Assessment of Deformed Tanks with Fluid Induced Loads
 
Call Girls in South Ex (delhi) call me [🔝9953056974🔝] escort service 24X7
Call Girls in South Ex (delhi) call me [🔝9953056974🔝] escort service 24X7Call Girls in South Ex (delhi) call me [🔝9953056974🔝] escort service 24X7
Call Girls in South Ex (delhi) call me [🔝9953056974🔝] escort service 24X7
 
Design For Accessibility: Getting it right from the start
Design For Accessibility: Getting it right from the startDesign For Accessibility: Getting it right from the start
Design For Accessibility: Getting it right from the start
 
Online electricity billing project report..pdf
Online electricity billing project report..pdfOnline electricity billing project report..pdf
Online electricity billing project report..pdf
 

Core Data with Swift 3.0

  • 1. Core Data with Swift 3 Capital One Engineering Tech Talks Korhan Bircan Senior Engineering Manager, Capital One
  • 2. Roadmap • Persistent Store Types • What is Core Data? • Demos • App Architecture • Core Data setup and common operations • Concurrency • Migration • Faults and Failures • Core Data vs Realm
  • 3. Persistent Store Types Store type Speed Object graph in memory Other XML Slow Whole Externally parsableBinary Fast Whole N/A SQLite Fast Partial N/A In-memory Fast Whole No storage required
  • 4. What Is Core Data? • Framework that helps manage the object life cycle and object graph management, including persistence • Grouping, filtering, and organization of data • Change tracking • Lazy loading of objects • User interface synchronization
  • 5. Demo - No Persistence
  • 6. Demo - Core Data
  • 10. Core Data Stack Diagram courtesy of Apple
  • 11. • Entity, attribute • Managed Object, Managed Object Context • Managed Object Model • Persistent Store: NSQLiteStoreType (non-atomic), NSXMLStoreType (macOS, atomic), NSBinaryStoreType (atomic), NSInMemoryStoreType (atomic), NSIncrementalStore (JSON, CSV?) • Persistent Store Coordinator • Relationships • Fetch Request, Predicate, Sort Descriptor • Fetched Results Controller Core Data Stack • Persistent Store Container
  • 12. Setup (Swift 2.3) lazy var applicationDocumentsDirectory: NSURL = { // The directory the application uses to store the Core Data store file. This code uses a directory named "CapitalOne.Delete" in the application's documents Application Support directory. let urls = NSFileManager.defaultManager().URLsForDirectory(.DocumentDirectory, inDomains: .UserDomainMask) return urls[urls.count-1] }() lazy var managedObjectModel: NSManagedObjectModel = { // The managed object model for the application. This property is not optional. It is a fatal error for the application not to be able to find and load its model. let modelURL = NSBundle.mainBundle().URLForResource("Delete", withExtension: "momd")! return NSManagedObjectModel(contentsOfURL: modelURL)! }() lazy var persistentStoreCoordinator: NSPersistentStoreCoordinator = { // The persistent store coordinator for the application. This implementation creates and returns a coordinator, having added the store for the application to it. This property is optional since there are legitimate error conditions that could cause the creation of the store to fail. // Create the coordinator and store let coordinator = NSPersistentStoreCoordinator(managedObjectModel: self.managedObjectModel) let url = self.applicationDocumentsDirectory.URLByAppendingPathComponent("SingleViewCoreData.sqlite") var failureReason = "There was an error creating or loading the application's saved data." do { try coordinator.addPersistentStoreWithType(NSSQLiteStoreType, configuration: nil, URL: url, options: nil) } catch { // Report any error we got. var dict = [String: AnyObject]() dict[NSLocalizedDescriptionKey] = "Failed to initialize the application's saved data" dict[NSLocalizedFailureReasonErrorKey] = failureReason dict[NSUnderlyingErrorKey] = error as NSError let wrappedError = NSError(domain: "YOUR_ERROR_DOMAIN", code: 9999, userInfo: dict) // Replace this with code to handle the error appropriately. // abort() causes the application to generate a crash log and terminate. You should not use this function in a shipping application, although it may be useful during development. NSLog("Unresolved error (wrappedError), (wrappedError.userInfo)") abort() } return coordinator }() lazy var managedObjectContext: NSManagedObjectContext = { // Returns the managed object context for the application (which is already bound to the persistent store coordinator for the application.) This property is optional since there are legitimate error conditions that could cause the creation of the context to fail. let coordinator = self.persistentStoreCoordinator var managedObjectContext = NSManagedObjectContext(concurrencyType: .MainQueueConcurrencyType) managedObjectContext.persistentStoreCoordinator = coordinator return managedObjectContext }() // MARK: - Core Data Saving support func saveContext () { if managedObjectContext.hasChanges { do { try managedObjectContext.save() } catch { // Replace this implementation with code to handle the error appropriately. // abort() causes the application to generate a crash log and terminate. You should not use this function in a shipping application, although it may be useful during development. let nserror = error as NSError NSLog("Unresolved error (nserror), (nserror.userInfo)") abort() } } }
  • 13. Setup (Swift 3) lazy var managedContext: NSManagedObjectContext = { let context = self.storeContainer.viewContext context.mergePolicy = NSMergeByPropertyObjectTrumpMergePolicy return context }() lazy var storeContainer: NSPersistentContainer = { let container = NSPersistentContainer(name: self.modelName) container.loadPersistentStores { (storeDescription, error) in if let error = error as NSError? { print("Unresolved error (error), (error.userInfo)") } else { print("Persistent store location: (storeDescription.url?.absoluteString)") } } return container }() func saveContext () { guard managedContext.hasChanges else { return } do { try self.managedContext.save() } catch let error as NSError { print("Unresolved error (error), (error.userInfo)") } }
  • 15. Saving and Retrieving Objects Save let tweet = Tweet(context: context) try! managedObjectContext.save() Retrieve let request: NSFetchRequest<Tweet> = Tweet.fetchRequest() let allTweets = try! context.fetch(request) Delete try! managedObjectContext.delete(tweet) try! managedObjectContext.save() Filter let fetchRequest = Tweet.fetchRequest() fetchRequest.predicate = NSPredicate(format: "text contains[c] %@", keyword) fetchRequest.sortDescriptors = [NSSortDescriptor(key: #keyPath(Tweet.createdAt), ascending: false)] try! fetchedResultsController?.performFetch()
  • 16. Fetch Predicates class Person: NSObject { let firstName: String let lastName: String let age: Int } let bobPredicate = NSPredicate(format: "firstName = 'Bob'") // let smithPredicate = NSPredicate(format: "lastName = %@", "Smith") // let thirtiesPredicate = NSPredicate(format: "age >= 30") fetchRequest.predicate = bobPredicate try! fetchedResultsController?.performFetch() • Basic Comparisons =, ==; >=, =>; <=, =<; >; <; != • Compound Predicates AND, &&; OR, ||; NOT, ! • String Comparisons BEGINSWITH; CONTAINS; ENDSWITH; LIKE; MATCHES
  • 17. Fetched Results Controller let fetchRequest.predicate = keyword.isEmpty ? nil : NSPredicate(format: "text contains[c] %@", keyword) fetchRequest.sortDescriptors = [NSSortDescriptor(key: #keyPath(Tweet.createdAt), ascending: false)] let fetchedResultsController = NSFetchedResultsController(fetchRequest: fetchRequest, managedObjectContext: CoreDataStack.sharedInstance.managedContext, sectionNameKeyPath: nil, cacheName: nil) do { try fetchedResultsController?.performFetch() } catch let error as NSError { print("Fetching error: (error), (error.userInfo)") }
  • 18. Wiring Model to UI override func numberOfSections(in tableView: UITableView) -> Int { return fetchedResultsController.sections } override func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int { return fetchedResultsController.sections?[section].numberOfObjects } override func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell { let cell = tableView.dequeueReusableCell(withIdentifier: TweetCell.identifier, for: indexPath) if let tweet = fetchedResultsController.object(at: indexPath) { TimelineViewCellAdapter.configure(cell as? TweetCell, tweet: tweet) } return cell } override func tableView(_ tableView: UITableView, titleForHeaderInSection section: Int) -> String? { let sectionInfo = fetchedResultsController.sections[section] return sectionInfo?.name }
  • 19. Communicating Data Changes func controllerWillChangeContent(controller: NSFetchedResultsController) { tableView.beginUpdates() } func controller(controller: NSFetchedResultsController, didChangeSection sectionInfo: NSFetchedResultsSectionInfo, atIndex sectionIndex: Int, forChangeType type: NSFetchedResultsChangeType) { switch type { case .Insert: tableView.insertSections(NSIndexSet(index: sectionIndex), withRowAnimation: .Fade) case .Delete: tableView.deleteSections(NSIndexSet(index: sectionIndex), withRowAnimation: .Fade) case .Move: break case .Update: break } } func controller(controller: NSFetchedResultsController, didChangeObject anObject: AnyObject, atIndexPath indexPath: NSIndexPath?, forChangeType type: NSFetchedResultsChangeType, newIndexPath: NSIndexPath?) { switch type { case .Insert: tableView.insertRowsAtIndexPaths([newIndexPath!], withRowAnimation: .Fade) case .Delete: tableView.deleteRowsAtIndexPaths([indexPath!], withRowAnimation: .Fade) case .Update: configureCell(tableView.cellForRowAtIndexPath(indexPath!)!, indexPath: indexPath!) case .Move: tableView.moveRowAtIndexPath(indexPath!, toIndexPath: newIndexPath!) } } func controllerDidChangeContent(controller: NSFetchedResultsController) { tableView.endUpdates() }
  • 20. Concurrency let jsonArray = … //JSON data to be imported into Core Data let moc = … //Our primary context on the main queue let privateMOC = NSManagedObjectContext(concurrencyType: .PrivateQueueConcurrencyType) privateMOC.parentContext = moc privateMOC.performBlock { for jsonObject in jsonArray { let mo = … //Managed object that matches the incoming JSON structure //update managed object with data from the dictionary } do { try privateMOC.save() moc.performBlockAndWait { do { try moc.save() } catch { fatalError("Failure to save context: (error)") } } } catch { fatalError("Failure to save context: (error)") } }
  • 22. Swift 2.3 vs Swift 3 dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), { do { let json = try NSJSONSerialization.JSONObjectWithData(data!, options: []) TimelineResponseMapper.parseResponse(json) dispatch_async(dispatch_get_main_queue(), { self.tableView.reloadData() }) } catch let jsonError as NSError { print("json error: (jsonError.localizedDescription)") } }) // vs DispatchQueue.global(qos: DispatchQoS.QoSClass.default).async { do { let json = try JSONSerialization.jsonObject(with: data!, options: []) TimelineResponseMapper.parseResponse(json) DispatchQueue.main.async { self.tableView.reloadData() } } catch let jsonError as NSError { print("json error: (jsonError.localizedDescription)") } }
  • 23. Tidbits • Multiple managed object contexts • Migration • Faulting and uniquing • Concurrency failures
  • 24. Migration lazy var storeContainer: NSPersistentContainer = { let container = NSPersistentContainer(name: self.modelName) container.loadPersistentStores { (storeDescription, error) in storeDescription.shouldMigrateStoreAutomatically = true storeDescription.shouldInferMappingModelAutomatically = true
  • 25. Why faults? • Dictionary definition: 1. (noun) an unattractive or unsatisfactory feature, esp. in a piece of work or in a person’s character. 2. (noun) responsibility for an accident or misfortune. 3. (noun) an extended break in a body of rock, marked by the relative displacement and discontinuity of strata on either side of a particular surface. • Apple’s definition: • A fault is a placeholder object that represents a managed object that has not yet been fully realized, or a collection object that represents a relationship.
  • 27. Why Faults May Fail 2016-10-11 22:20:24.530 CoreDataTest[24222:60b] * Assertion failure in -[AppDelegate save], .../AppDelegate.swift:28 2016-10-11 22:20:24.530 CoreDataTest[24222:60b] * Terminating app due to uncaught exception 'NSInternalInconsistencyException', reason: 'Save failed {type = immutable dict, count = 2, entries => 1 : {contents = "NSAffectedObjectsErrorKey"} = ( " (entity: Tweet; id: 0x6b8bf10 ; data: )" ) 2 : {contents = "NSUnderlyingException"} = CoreData could not fulfill a fault for '0x6b8bf10 ' }
  • 28. Handling Fault Failures • managedObjectContext.shouldDeleteInaccessibleFaults • Prefetch everything • Write lots of code (existingobjectwithId() to make sure the object is in the database before referencing it) • Use query generators
  • 29. Concurrency Failures let firstTweet = Tweet(context: managedContext) // Synchronously performs the block on the context's queue. //May safely be called reentrantly. managedContext.performAndWait { do { firstTweet.text = "Something interesting happened today..." try self.managedContext.save() } catch let error as NSError { print("Unresolved error (error), (error.userInfo)") } } managedContext2.performAndWait { let text = firstTweet.text print(text) } 2016-10-11 22:20:24.530 CoreDataTest[24222:60b] CoreData concurrency failure
  • 30. Realm CoreData Realm Save let tweet = Tweet(context: context) try! managedObjectContext.save() let realm = try! Realm() let tweet = Tweet() try! realm.write { realm.add(tweet) } Retrieve let request: NSFetchRequest<Tweet> = Tweet.fetchRequest() let allTweets = try! context.fetch(request) let tweets = realm.objects(Tweet.self) Delete try! managedObjectContext.delete(tweet) try! managedObjectContext.save() try! realm.write { realm.delete(tweet) } Filter let fetchRequest = Tweet.fetchRequest() fetchRequest.predicate = NSPredicate(format: "text contains[c] %@", keyword) fetchRequest.sortDescriptors = [NSSortDescriptor(key: #keyPath(Tweet.createdAt), ascending: false)] try! fetchedResultsController?.performFetch() let predicate = NSPredicate(format: "text contains[c] %@", keyword) let tweets = realm.objects(Tweet.self).filter(predicate) let sortedTweets = tweets.sorted("createdAt", ascending: ascending)
  • 31. Core Data vs Realm Core Data Realm Latest Swift compatibility Future proof Ease of use Multithreading Speed Encryption Support Real life testing
  • 32. Next Time • Persisting Data in the Cloud