我想删除我的sql lite文件并再次设置persistance存储。
//Explicitly write Core Data accessors
- (NSManagedObjectContext *) managedObjectContext {
if (managedObjectContext != nil) {
return managedObjectContext;
}
NSPersistentStoreCoordinator *coordinator = [self persistentStoreCoordinator];
if (coordinator != nil) {
managedObjectContext = [[NSManagedObjectContext alloc] init];
[managedObjectContext setPersistentStoreCoordinator: coordinator];
}
return managedObjectContext;
}
- (void) setManagedObjectContext:(NSManagedObjectContext *)managedObjectContext{}
- (NSManagedObjectModel *)managedObjectModel {
if (managedObjectModel != nil) {
return managedObjectModel;
}
managedObjectModel = [NSManagedObjectModel mergedModelFromBundles:nil] ;
return managedObjectModel;
}
-(void) setManagedObjectModel:(NSManagedObjectModel *)managedObjectModel{}
- (NSPersistentStoreCoordinator *)persistentStoreCoordinator {
if (persistentStoreCoordinator != nil) {
return persistentStoreCoordinator;
}
NSURL *storeUrl = [NSURL fileURLWithPath: [[self applicationDocumentsDirectory] stringByAppendingPathComponent: @"Port.sqlite"]];
NSError *error = nil;
persistentStoreCoordinator = [[NSPersistentStoreCoordinator alloc] initWithManagedObjectModel:[self managedObjectModel]];
if(![persistentStoreCoordinator addPersistentStoreWithType:NSSQLiteStoreType configuration:nil URL:storeUrl options:nil error:&error]) {
NSLog(@"Could not create store .... %@", error );
/*Error for store creation should be handled in here*/
}
return persistentStoreCoordinator;
}
我正在尝试像这样重置我的场景
- (void)reset {
// Release CoreData chain
self.managedObjectContext = nil;
self.managedObjectModel = nil;
self.persistentStoreCoordinator = nil;
// Delete the sqlite file
NSError *error = nil;
NSFileManager *fileManager = [NSFileManager defaultManager];
NSURL *storeUrl = [NSURL fileURLWithPath: [[self applicationDocumentsDirectory] stringByAppendingPathComponent: @"Port.sqlite"]];
if ([fileManager fileExistsAtPath:storeUrl.path]){
[fileManager removeItemAtURL:storeUrl error:&error];
}
self.managedObjectContext = [self managedObjectContext];
self.managedObjectModel = [self managedObjectModel];
self.persistentStoreCoordinator = [self persistentStoreCoordinator];
// handle error...
}
我在保存时遇到错误:
+ (BOOL)saveAll {
// [self createStorage];
NSError *error = nil;
NSManagedObjectContext *managedObjectContext = [(WSSMobileAppsAppDelegate *)[[UIApplication sharedApplication] delegate] managedObjectContext];
if (![managedObjectContext save:&error]) {
NSLog(@"Error while saving %@", error);
return FALSE;
}
return TRUE;
}
错误:
Error while saving Error Domain=NSCocoaErrorDomain Code=134030 "The operation couldn’t be completed. (Cocoa error 134030.)" UserInfo=0x7195ac0 {NSAffectedStoresErrorKey=(
"<NSSQLCore: 0x714eee0> (URL: file://localhost/Users/.../Library/Application%20Support/iPhone%20Simulator/5.0/Applications/CEDB9019-1D64-4968-9BE7-57E1493B96EC/Documents/Port.sqlite)"
), NSUnderlyingError=0x7195a50 "The operation couldn’t be completed. (Cocoa error 4.)", NSFilePath=/Users/.../Library/Application Support/iPhone Simulator/5.0/Applications/CEDB9019-1D64-4968-9BE7-57E1493B96EC/Documents/Port.sqlite}
如果我运行我的重置功能,我只会收到错误。我想的那样:
self.managedObjectContext = nil;
self.managedObjectModel = nil;
self.persistentStoreCoordinator = nil;
......会解决问题。然后一切都将被重建。请帮忙。
非常感谢您的回答。现在没有错误,但如果我运行我的重置,则不会存储任何内容。我在保存后立即进行取件
if (![managedObjectContext save:&error]) {
NSLog(@"Error while saving %@", error);
return FALSE;
}
CoreDataPortService *c = [[CoreDataPortService alloc] init];
NSLog(@"Saved all.... got number of ports ... %d", [[c getPorts] count]);
我如果不运行我的重置方法,一切都按预期工作。什么可能是错的?
答案 0 :(得分:0)
您为managedObjectContext编写了一个setter,但它什么也没做:
- (void) setManagedObjectContext:(NSManagedObjectContext *)managedObjectContext{}
执行self.managedObjectContext = nil
后,只需拨打[self setManagedObjectContext:nil]
即可。这没什么。实例变量managedObjectContext保持相同的值,当您使用getter再次请求它时,您仍然拥有与已删除文件关联的managedObjectContext。你需要:
- (void) setManagedObjectContext:(NSManagedObjectContext *)_managedObjectContext {
[managedObjectContext release];
managedObjectContext = _managedObjectContext;
[managedObjectContext retain];
}
这也是假设您的managedObjectContext属性是使用非原子修饰符声明的。如果它被声明为原子,你还需要锁定代码。以类似的方式为managedObjectModel和persistentStoreCoordinator编写setter。
@synthesize通常为你生成这样的setter,但是既然你想编写自己的getter,你也必须编写自己的setter。可能有办法让@synthesize只为你的属性制作一个setter,但我不记得了。
回答问题。也许你正在做这样的事情:
NSManagedObjectContext *moc = self.managedObjectContext;
[self reset];
[self repopulateData:xmlFile];
NSError *error = nil;
if (![moc save:&error])
[self logError:error];
如果是这种情况,那么您将在旧的托管对象上下文中调用save。不确定结果会是什么。而是将倒数第二行更改为
if (![self.managedObjectContext save:&error])
确保使用当前的托管对象上下文。
或者类似地,您可能尝试从旧的托管对象上下文中读取。检查您正在使用的任何托管对象上下文指针的地址,并确保它们指向与您在重置时创建的新托管对象上下文相同的内容。
如果那不是问题,我不知道。您将不得不尝试收集有关它无法正常工作的更多信息。例如,该文件是否存在?添加数据时其大小是否会增加?是将数据写入文件,但无法读取?