SlideShare a Scribd company logo
1 of 32
Core Data
-Version & Migration
Michael Pan
13年8月15⽇日星期四
Migration
• Automatic (Lightweight) Migration
• Manual Migration
13年8月15⽇日星期四
Lightweight migration can do
• Adding or removing an entity, attribute or relationship
• Make an attribute non-optional with a default value
• Making a non-optional attribute optional
• Renaming an entity or attribute using a renaming identifier
13年8月15⽇日星期四
Create master-detail application
13年8月15⽇日星期四
Check Core Data
13年8月15⽇日星期四
Run it
13年8月15⽇日星期四
Select core data model
13年8月15⽇日星期四
Add ModelVersion
13年8月15⽇日星期四
Version name
13年8月15⽇日星期四
ModifyVersion 2
Entity : Event => Record
13年8月15⽇日星期四
Change the version
13年8月15⽇日星期四
Run - Crash
Unresolved error Error Domain=NSCocoaErrorDomain Code=134100 "The operation couldn’t be completed. (Cocoa error
134100.)" UserInfo=0x834a9f0 {metadata={
NSPersistenceFrameworkVersion = 419;
NSStoreModelVersionHashes = {
Event = <5431c046 d30e7f32 c2cc8099 58add1e7 579ad104 a3aa8fc4 846e97d7 af01cc79>;
};
NSStoreModelVersionHashesVersion = 3;
NSStoreModelVersionIdentifiers = (
""
);
NSStoreType = SQLite;
NSStoreUUID = "E8AAA7FE-4F73-4D13-B7F2-451C0F487E21";
"_NSAutoVacuumLevel" = 2;
}, reason=The model used to open the store is incompatible with the one used to create the store}, {
metadata = {
NSPersistenceFrameworkVersion = 419;
NSStoreModelVersionHashes = {
Event = <5431c046 d30e7f32 c2cc8099 58add1e7 579ad104 a3aa8fc4 846e97d7 af01cc79>;
};
NSStoreModelVersionHashesVersion = 3;
NSStoreModelVersionIdentifiers = (
""
);
NSStoreType = SQLite;
NSStoreUUID = "E8AAA7FE-4F73-4D13-B7F2-451C0F487E21";
"_NSAutoVacuumLevel" = 2;
};
reason = "The model used to open the store is incompatible with the one used to create the store";
}
13年8月15⽇日星期四
Enable auto migration
• AppDelegate.m
• - (NSPersistentStoreCoordinator *)persistentStoreCoordinator
NSMutableDictionary *options = [NSMutableDictionary dictionary];
[options setValue:@YES forKey:NSMigratePersistentStoresAutomaticallyOption];
[options setValue:@YES forKey:NSInferMappingModelAutomaticallyOption];
if (![_persistentStoreCoordinator
addPersistentStoreWithType:NSSQLiteStoreType configuration:nil URL:storeURL
options:options error:&error]) {
// ignore...
}
13年8月15⽇日星期四
Crash again
Terminating app due to uncaught exception
'NSInvalidArgumentException', reason:
'executeFetchRequest:error: A fetch request must
have an entity.'
13年8月15⽇日星期四
Change Entity name
• MasterViewController.m
- (NSFetchedResultsController *)fetchedResultsController
{
if (_fetchedResultsController != nil) {
return _fetchedResultsController;
}
NSFetchRequest *fetchRequest = [[NSFetchRequest alloc] init];
// Edit the entity name as appropriate.
NSEntityDescription *entity = [NSEntityDescription entityForName:@"Record"
inManagedObjectContext:self.managedObjectContext];
[fetchRequest setEntity:entity];
// ignore ...
}
13年8月15⽇日星期四
Run - ok
13年8月15⽇日星期四
Delete all data first
• remove original codes
• MasterViewController.m
- (void)viewDidLoad
{
[super viewDidLoad];
! // Do any additional setup after loading the view, typically from a nib.
self.navigationItem.leftBarButtonItem = self.editButtonItem;
// UIBarButtonItem *addButton = [[UIBarButtonItem alloc]
initWithBarButtonSystemItem:UIBarButtonSystemItemAdd target:self
action:@selector(insertNewObject:)];
// self.navigationItem.rightBarButtonItem = addButton;
}
13年8月15⽇日星期四
Change display
13年8月15⽇日星期四
Model v3
V3 V2
13年8月15⽇日星期四
NewRecordViewController
13年8月15⽇日星期四
Add NewViewController
@interface NewRecordViewController : UIViewController
@property (weak, nonatomic) IBOutlet UITextField *commentField;
@property (weak, nonatomic) IBOutlet UITextView *tagsView;
@property (strong) NSManagedObjectContext * context;
@end
13年8月15⽇日星期四
- (IBAction)addNewRecord:(id)sender {
NSManagedObject * newRecord = [NSEntityDescription
insertNewObjectForEntityForName:@"Record" inManagedObjectContext:self.context];
self.recordComment = self.commentField.text;
[newRecord setValue:self.recordComment forKey:@"comment"];
[newRecord setValue:self.recordTags forKey:@"tags"];
NSError * error;
if (![self.context save:&error]) {
if (error) {
NSLog(@"Fail to create new record");
}
}else{
[self.navigationController popViewControllerAnimated:YES];
}
}
Add new record
13年8月15⽇日星期四
Add tag
13年8月15⽇日星期四
TagViewController.h
@protocol TagViewControllerDelegate;
@interface TagViewController : UITableViewController
@property (strong) NSManagedObjectContext * context;
@property (weak) id<TagViewControllerDelegate> delegate;
@end
@protocol TagViewControllerDelegate <NSObject>
-(void) tagView:(TagViewController *) tagView insertNewTag:(NSManagedObject *) tag;
@end
13年8月15⽇日星期四
TagViewController.m
-(void) fetchAllTags{
NSFetchRequest *fetchRequest = [[NSFetchRequest alloc] init];
NSEntityDescription *entity = [NSEntityDescription entityForName:@"Tag"
inManagedObjectContext:self.context];
[fetchRequest setEntity:entity];
[fetchRequest setFetchBatchSize:20];
NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"name"
ascending:NO];
NSArray *sortDescriptors = @[sortDescriptor];
[fetchRequest setSortDescriptors:sortDescriptors];
NSError * error;
self.tags = [[self.context executeFetchRequest:fetchRequest error:&error]
mutableCopy];
if (error) {
NSLog(@"Can not fetch tags");
}
}
13年8月15⽇日星期四
Add new tag
-(void) insertNewTag:(NSString *) tagName{
NSManagedObject * newTag = [NSEntityDescription
insertNewObjectForEntityForName:@"Tag" inManagedObjectContext:self.context];
[newTag setValue:tagName forKey:@"name"];
NSError * error;
if(![self.context save:&error]){
if (error) {
NSLog(@"Fail to create new tag");
}
}else{
[self.tags addObject:newTag];
[self.tableView reloadData];
}
}
13年8月15⽇日星期四
Send tags to NewRecordViewController
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:
(NSIndexPath *)indexPath
{
if ([self.delegate respondsToSelector:@selector(tagView:insertNewTag:)]) {
[self.delegate tagView:self insertNewTag:self.tags[indexPath.row]];
}
}
13年8月15⽇日星期四
Receive tags in NewRecordViewController
-(void) tagView:(TagViewController *)tagView insertNewTag:(NSManagedObject *)tag{
[self.recordTags addObject:tag];
NSSortDescriptor * sortDescriptor = [NSSortDescriptor
sortDescriptorWithKey:@"name" ascending:YES];
NSSet * nameSet = self.recordTags ;
NSArray * sortedArray = [nameSet
sortedArrayUsingDescriptors:@[sortDescriptor]];
self.tagsView.text = [NSString stringWithFormat:@"%@",[[sortedArray
valueForKey:@"name" ] componentsJoinedByString:@","]];
[self.navigationController popViewControllerAnimated:YES];
}
13年8月15⽇日星期四
Demo - BookingApp
13年8月15⽇日星期四
SQLite debug message
13年8月15⽇日星期四
Delete some version
• Remove .xcdatamodeld (Remove Reference Only)
• Open project in the finder
• find out .xcdatamodeld
• Right-click -> Show Package Contents
• Delete what you want to delete
13年8月15⽇日星期四
Question
13年8月15⽇日星期四

More Related Content

Similar to Core data lightweight_migration

YUIconf2010介绍
YUIconf2010介绍YUIconf2010介绍
YUIconf2010介绍
ling yu
 
Manual instruction apc3.0
Manual instruction apc3.0Manual instruction apc3.0
Manual instruction apc3.0
ahnlabchina
 

Similar to Core data lightweight_migration (20)

不断归零的前端人生 - 2016 中国软件开发者大会
不断归零的前端人生 - 2016 中国软件开发者大会不断归零的前端人生 - 2016 中国软件开发者大会
不断归零的前端人生 - 2016 中国软件开发者大会
 
I os 07
I os 07I os 07
I os 07
 
I os 16
I os 16I os 16
I os 16
 
005
005005
005
 
I os 01
I os 01I os 01
I os 01
 
15 Subclassing UITableViewCell
15 Subclassing UITableViewCell15 Subclassing UITableViewCell
15 Subclassing UITableViewCell
 
13 UIPopoverController and Modal View Controller
13 UIPopoverController and Modal View Controller13 UIPopoverController and Modal View Controller
13 UIPopoverController and Modal View Controller
 
11 UINavigationController
11 UINavigationController11 UINavigationController
11 UINavigationController
 
I os 09
I os 09I os 09
I os 09
 
製作 Unity Plugin for iOS
製作 Unity Plugin for iOS製作 Unity Plugin for iOS
製作 Unity Plugin for iOS
 
004-Assembly Design 組立設計
004-Assembly Design 組立設計004-Assembly Design 組立設計
004-Assembly Design 組立設計
 
jQuery Mobile
jQuery MobilejQuery Mobile
jQuery Mobile
 
12 Camera
12 Camera12 Camera
12 Camera
 
I os 10
I os 10I os 10
I os 10
 
YUIconf2010介绍
YUIconf2010介绍YUIconf2010介绍
YUIconf2010介绍
 
I os 02
I os 02I os 02
I os 02
 
YUI 3 菜鳥救星
YUI 3 菜鳥救星YUI 3 菜鳥救星
YUI 3 菜鳥救星
 
Angular 7 全新功能探索 (Angular Taiwan 2018)
Angular 7 全新功能探索 (Angular Taiwan 2018)Angular 7 全新功能探索 (Angular Taiwan 2018)
Angular 7 全新功能探索 (Angular Taiwan 2018)
 
Manual instruction apc3.0
Manual instruction apc3.0Manual instruction apc3.0
Manual instruction apc3.0
 
iOS App 開發 -- Storybard 基礎練習、APP 上架、IAP
iOS App 開發 -- Storybard 基礎練習、APP 上架、IAPiOS App 開發 -- Storybard 基礎練習、APP 上架、IAP
iOS App 開發 -- Storybard 基礎練習、APP 上架、IAP
 

More from Michael Pan (15)

Activity
ActivityActivity
Activity
 
Shootting Game
Shootting GameShootting Game
Shootting Game
 
Introduction to Android Studio
Introduction to Android StudioIntroduction to Android Studio
Introduction to Android Studio
 
Eclipse and Genymotion
Eclipse and GenymotionEclipse and Genymotion
Eclipse and Genymotion
 
Note something
Note somethingNote something
Note something
 
Google maps SDK for iOS 1.4
Google maps SDK for iOS 1.4Google maps SDK for iOS 1.4
Google maps SDK for iOS 1.4
 
Objc under the_hood_2013
Objc under the_hood_2013Objc under the_hood_2013
Objc under the_hood_2013
 
Prototype by Xcode
Prototype by XcodePrototype by Xcode
Prototype by Xcode
 
Dropbox sync
Dropbox syncDropbox sync
Dropbox sync
 
Nimbus
NimbusNimbus
Nimbus
 
Superstar dj pdf
Superstar dj pdfSuperstar dj pdf
Superstar dj pdf
 
ADB - Arthur
ADB - ArthurADB - Arthur
ADB - Arthur
 
Appsgaga - iOS Game Developer
Appsgaga - iOS Game DeveloperAppsgaga - iOS Game Developer
Appsgaga - iOS Game Developer
 
GZFox Inc. Jacky
GZFox Inc. JackyGZFox Inc. Jacky
GZFox Inc. Jacky
 
創投公司 hoku_20121017
創投公司 hoku_20121017創投公司 hoku_20121017
創投公司 hoku_20121017
 

Core data lightweight_migration

  • 1. Core Data -Version & Migration Michael Pan 13年8月15⽇日星期四
  • 2. Migration • Automatic (Lightweight) Migration • Manual Migration 13年8月15⽇日星期四
  • 3. Lightweight migration can do • Adding or removing an entity, attribute or relationship • Make an attribute non-optional with a default value • Making a non-optional attribute optional • Renaming an entity or attribute using a renaming identifier 13年8月15⽇日星期四
  • 7. Select core data model 13年8月15⽇日星期四
  • 10. ModifyVersion 2 Entity : Event => Record 13年8月15⽇日星期四
  • 12. Run - Crash Unresolved error Error Domain=NSCocoaErrorDomain Code=134100 "The operation couldn’t be completed. (Cocoa error 134100.)" UserInfo=0x834a9f0 {metadata={ NSPersistenceFrameworkVersion = 419; NSStoreModelVersionHashes = { Event = <5431c046 d30e7f32 c2cc8099 58add1e7 579ad104 a3aa8fc4 846e97d7 af01cc79>; }; NSStoreModelVersionHashesVersion = 3; NSStoreModelVersionIdentifiers = ( "" ); NSStoreType = SQLite; NSStoreUUID = "E8AAA7FE-4F73-4D13-B7F2-451C0F487E21"; "_NSAutoVacuumLevel" = 2; }, reason=The model used to open the store is incompatible with the one used to create the store}, { metadata = { NSPersistenceFrameworkVersion = 419; NSStoreModelVersionHashes = { Event = <5431c046 d30e7f32 c2cc8099 58add1e7 579ad104 a3aa8fc4 846e97d7 af01cc79>; }; NSStoreModelVersionHashesVersion = 3; NSStoreModelVersionIdentifiers = ( "" ); NSStoreType = SQLite; NSStoreUUID = "E8AAA7FE-4F73-4D13-B7F2-451C0F487E21"; "_NSAutoVacuumLevel" = 2; }; reason = "The model used to open the store is incompatible with the one used to create the store"; } 13年8月15⽇日星期四
  • 13. Enable auto migration • AppDelegate.m • - (NSPersistentStoreCoordinator *)persistentStoreCoordinator NSMutableDictionary *options = [NSMutableDictionary dictionary]; [options setValue:@YES forKey:NSMigratePersistentStoresAutomaticallyOption]; [options setValue:@YES forKey:NSInferMappingModelAutomaticallyOption]; if (![_persistentStoreCoordinator addPersistentStoreWithType:NSSQLiteStoreType configuration:nil URL:storeURL options:options error:&error]) { // ignore... } 13年8月15⽇日星期四
  • 14. Crash again Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: 'executeFetchRequest:error: A fetch request must have an entity.' 13年8月15⽇日星期四
  • 15. Change Entity name • MasterViewController.m - (NSFetchedResultsController *)fetchedResultsController { if (_fetchedResultsController != nil) { return _fetchedResultsController; } NSFetchRequest *fetchRequest = [[NSFetchRequest alloc] init]; // Edit the entity name as appropriate. NSEntityDescription *entity = [NSEntityDescription entityForName:@"Record" inManagedObjectContext:self.managedObjectContext]; [fetchRequest setEntity:entity]; // ignore ... } 13年8月15⽇日星期四
  • 17. Delete all data first • remove original codes • MasterViewController.m - (void)viewDidLoad { [super viewDidLoad]; ! // Do any additional setup after loading the view, typically from a nib. self.navigationItem.leftBarButtonItem = self.editButtonItem; // UIBarButtonItem *addButton = [[UIBarButtonItem alloc] initWithBarButtonSystemItem:UIBarButtonSystemItemAdd target:self action:@selector(insertNewObject:)]; // self.navigationItem.rightBarButtonItem = addButton; } 13年8月15⽇日星期四
  • 21. Add NewViewController @interface NewRecordViewController : UIViewController @property (weak, nonatomic) IBOutlet UITextField *commentField; @property (weak, nonatomic) IBOutlet UITextView *tagsView; @property (strong) NSManagedObjectContext * context; @end 13年8月15⽇日星期四
  • 22. - (IBAction)addNewRecord:(id)sender { NSManagedObject * newRecord = [NSEntityDescription insertNewObjectForEntityForName:@"Record" inManagedObjectContext:self.context]; self.recordComment = self.commentField.text; [newRecord setValue:self.recordComment forKey:@"comment"]; [newRecord setValue:self.recordTags forKey:@"tags"]; NSError * error; if (![self.context save:&error]) { if (error) { NSLog(@"Fail to create new record"); } }else{ [self.navigationController popViewControllerAnimated:YES]; } } Add new record 13年8月15⽇日星期四
  • 24. TagViewController.h @protocol TagViewControllerDelegate; @interface TagViewController : UITableViewController @property (strong) NSManagedObjectContext * context; @property (weak) id<TagViewControllerDelegate> delegate; @end @protocol TagViewControllerDelegate <NSObject> -(void) tagView:(TagViewController *) tagView insertNewTag:(NSManagedObject *) tag; @end 13年8月15⽇日星期四
  • 25. TagViewController.m -(void) fetchAllTags{ NSFetchRequest *fetchRequest = [[NSFetchRequest alloc] init]; NSEntityDescription *entity = [NSEntityDescription entityForName:@"Tag" inManagedObjectContext:self.context]; [fetchRequest setEntity:entity]; [fetchRequest setFetchBatchSize:20]; NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"name" ascending:NO]; NSArray *sortDescriptors = @[sortDescriptor]; [fetchRequest setSortDescriptors:sortDescriptors]; NSError * error; self.tags = [[self.context executeFetchRequest:fetchRequest error:&error] mutableCopy]; if (error) { NSLog(@"Can not fetch tags"); } } 13年8月15⽇日星期四
  • 26. Add new tag -(void) insertNewTag:(NSString *) tagName{ NSManagedObject * newTag = [NSEntityDescription insertNewObjectForEntityForName:@"Tag" inManagedObjectContext:self.context]; [newTag setValue:tagName forKey:@"name"]; NSError * error; if(![self.context save:&error]){ if (error) { NSLog(@"Fail to create new tag"); } }else{ [self.tags addObject:newTag]; [self.tableView reloadData]; } } 13年8月15⽇日星期四
  • 27. Send tags to NewRecordViewController - (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath: (NSIndexPath *)indexPath { if ([self.delegate respondsToSelector:@selector(tagView:insertNewTag:)]) { [self.delegate tagView:self insertNewTag:self.tags[indexPath.row]]; } } 13年8月15⽇日星期四
  • 28. Receive tags in NewRecordViewController -(void) tagView:(TagViewController *)tagView insertNewTag:(NSManagedObject *)tag{ [self.recordTags addObject:tag]; NSSortDescriptor * sortDescriptor = [NSSortDescriptor sortDescriptorWithKey:@"name" ascending:YES]; NSSet * nameSet = self.recordTags ; NSArray * sortedArray = [nameSet sortedArrayUsingDescriptors:@[sortDescriptor]]; self.tagsView.text = [NSString stringWithFormat:@"%@",[[sortedArray valueForKey:@"name" ] componentsJoinedByString:@","]]; [self.navigationController popViewControllerAnimated:YES]; } 13年8月15⽇日星期四
  • 31. Delete some version • Remove .xcdatamodeld (Remove Reference Only) • Open project in the finder • find out .xcdatamodeld • Right-click -> Show Package Contents • Delete what you want to delete 13年8月15⽇日星期四