我在 CoreData 版本迁移中遇到了一个奇怪的错误。它崩溃了,我完全被难住了。我在我的 xcdatamodel 版本 2 中为一个子实体添加了两个新属性,并将其设置为当前版本。创建持久存储协调器的代码如下所示:
NSURL *modelURL = [[NSBundle mainBundle] URLForResource:@"MyModel" withExtension:@"momd"];
self.mainModel = [[NSManagedObjectModel alloc] initWithContentsOfURL:modelURL];
self.mainQueueManagedObjectContext = [[NSManagedObjectContext alloc] initWithConcurrencyType:NSMainQueueConcurrencyType];
self.persistentStoreCoordinator = [self storeCoordinatorForDB:@"MyDB.sqlite" objectModel:self.mainModel managedObjectContext:self.mainQueueManagedObjectContext];
- (NSPersistentStoreCoordinator *)storeCoordinatorForDB:(NSString *)dbName objectModel:(NSManagedObjectModel *)model managedObjectContext:(NSManagedObjectContext *)moc {
NSFileManager *fm = [NSFileManager defaultManager];
NSURL *storeURL = [[fm URLsForDirectory:NSApplicationSupportDirectory
inDomains:NSUserDomainMask] lastObject];
if (!storeURL) {
return nil;
}
else {
NSError *createError = nil;
BOOL createSuccess = [fm createDirectoryAtURL:storeURL withIntermediateDirectories:YES attributes:nil error:&createError];
if (!createSuccess) {
NSLog(@"Dir creation error: %@", createError);
}
}
storeURL = [storeURL URLByAppendingPathComponent:dbName];
NSURL *mainBundleDBURL = [[[NSBundle mainBundle] bundleURL] URLByAppendingPathComponent:dbName];
NSError *copyError = nil;
BOOL copySuccess = [fm copyItemAtURL:mainBundleDBURL toURL:storeURL error:©Error];
if (!copySuccess) {
NSLog(@"File copy error: %@", copyError);
}
NSError *error = nil;
NSPersistentStoreCoordinator *coordinator = [[NSPersistentStoreCoordinator alloc] initWithManagedObjectModel:model];
moc.persistentStoreCoordinator = coordinator;
NSPersistentStore *ps = [coordinator addPersistentStoreWithType:NSSQLiteStoreType configuration:nil URL:storeURL options:@{
NSMigratePersistentStoresAutomaticallyOption:@(YES),
NSInferMappingModelAutomaticallyOption:@(YES)
} error:&error];
if (!ps) {
NSLog(@"Unresolved error adding persistent store: %@", error);
return nil;
}
return coordinator;
}
MyDB.sqlite 是来自先前版本的 xcdatamodel 的预置 CoreData 文件。
这导致 EXC_BAD_ACCESS 在一个(据我所知)绝对虚假的地址,例如。0x0 或 0x16)
结果堆栈跟踪是:
Exception Type: EXC_BAD_ACCESS (SIGSEGV)
Exception Codes: KERN_INVALID_ADDRESS at 0x00000000
Crashed Thread: 0
Thread 0 name: Dispatch queue: com.apple.main-thread
Thread 0 Crashed:
0 libobjc.A.dylib 0x3b2f95d6 objc_msgSend + 22
1 CoreData 0x333e5274 -[NSFetchedPropertyDescription copyWithZone:] + 140
2 CoreData 0x333d8f62 -[NSEntityDescription copyWithZone:] + 682
3 CoreData 0x333d8e70 -[NSEntityDescription copyWithZone:] + 440
4 CoreData 0x3340f4a8 -[NSManagedObjectModel copyWithZone:] + 340
5 CoreData 0x3341d20e -[NSMigrationManager initWithSourceModel:destinationModel:] + 178
6 CoreData 0x3346dc5e -[NSStoreMigrationPolicy managerForSourceModel:destinationModel:error:] + 390
7 CoreData 0x3346f060 -[NSStoreMigrationPolicy(InternalMethods) _gatherDataAndPerformMigration:] + 1596
8 CoreData 0x3339235c -[NSPersistentStoreCoordinator addPersistentStoreWithType:configuration:URL:options:error:] + 3340
9 ActorsNetwork 0x000ba072 -[DataStore storeCoordinatorForDB:objectModel:managedObjectContext:] (DataStore.m:69)
有人知道发生了什么或有用的提示如何调试吗?我已经尝试过仪器分配,但没有进一步。
[已解决] 有点。我在模型中有一个获取的属性定义。删除修复了导入崩溃的问题。