ResKit:临时 NSManagedObjects
Posted
技术标签:
【中文标题】ResKit:临时 NSManagedObjects【英文标题】:ResKit: temporary NSManagedObjects 【发布时间】:2013-10-02 08:54:45 【问题描述】:经过长时间的研究,我正在写这篇文章,但我真的很难找到解决我问题的最佳方法。
我对 resKit 和 CoreData 都很陌生...无论如何,我正在映射并在 CoreData 中保存我从 Web 服务接收到的 JSON。
这里有一些代码:
//ResKit and Core Data initialization here
...
//Initialization RKObjectManager
RKObjectManager *objectManager = [RKObjectManager managerWithBaseURL:[NSURL URLWithString:@"http://http://www.myWebService.com"]];
objectManager.managedObjectStore = managedObjectStore;
[RKObjectManager setSharedManager:objectManager];
//Categories Mapping and descriptor
RKEntityMapping *categoriesMapping = [RKEntityMapping mappingForEntityForName:@"XNCategory" inManagedObjectStore:managedObjectStore];
[categoriesMapping addAttributeMappingsFromDictionary:@
@"id": @"idCategory",
@"desc": @"desc",
@"idFam":@"idFam"];
categoriesMapping.identificationAttributes = @[ @"idCategory" ];
RKResponseDescriptor *categoriesDescriptor = [RKResponseDescriptor responseDescriptorWithMapping:categoriesMapping
method:RKRequestMethodGET pathPattern:@"getData.asp" keyPath:@"categories"
statusCodes:RKStatusCodeIndexSetForClass(RKStatusCodeClassSuccessful)];
//Families Mapping and descriptor
RKEntityMapping *familiesMapping = [RKEntityMapping mappingForEntityForName:@"XNFamily" inManagedObjectStore:managedObjectStore];
[familiesMapping addAttributeMappingsFromDictionary:@
@"id": @"idFam",
@"desc": @"desc"];
familiesMapping.identificationAttributes = @[ @"idFam" ];
RKResponseDescriptor *familiesDescriptor = [RKResponseDescriptor responseDescriptorWithMapping:familiesMapping
method:RKRequestMethodGET pathPattern:@"getData.asp" keyPath:@"families"
statusCodes:RKStatusCodeIndexSetForClass(RKStatusCodeClassSuccessful)];
//Relation between the 2 mapping
NSEntityDescription *categoryEntity = [NSEntityDescription entityForName:@"XNCategory"
inManagedObjectContext:[managedObjectStore mainQueueManagedObjectContext]];
NSRelationshipDescription *userRelationshipFrom = [categoryEntity relationshipsByName][@"family"];
RKConnectionDescription *connectionUserMessageFrom = [[RKConnectionDescription alloc]
initWithRelationship:userRelationshipFrom attributes:@ @"idFam": @"idFam" ];
[categoriesMapping addConnection:connectionUserMessageFrom];
//Finally add the descriptor to the object manager
[objectManager addResponseDescriptor:categoriesDescriptor];
[objectManager addResponseDescriptor:familiesDescriptor];
在另一个视图控制器中,当我需要下载所有数据时,我只是这样做:
[[RKObjectManager sharedManager] getObjectsAtPath:@"getData.asp" parameters:@kAuthKeyName : kAuthKeyValue success:^(RKObjectRequestOperation *operation, RKMappingResult *mappingResult)
//Success block
failure:^(RKObjectRequestOperation *operation, NSError *error)
//Failure Block
];
此代码正确下载并自动保存到CoreData中的持久存储中,保留实体之间的关系。
现在我的问题是:有什么方法可以避免这种自动保存吗?因为我需要处理从webService检索到的数据,只有在我决定的时候才保存。
我发现这篇文章非常有用,或者至少给了我一个很好的开始研究的输入:Best practice for temporary objects in RestKit with Core Data,但这是 2012 年的一篇文章,我不知道是否发生了变化,或者现在是否有更好的解决方案。
换句话说,我需要的是一种允许使用 ResKit 进行映射的方法,因此,所有接收到的数据都将根据我创建的所有 NSRelationshipDescription 进行正确的实体映射,并且手动管理保存到持久存储。
非常感谢您的耐心和帮助。
【问题讨论】:
【参考方案1】:一般来说,您链接到的答案仍然有效。 RestKit 没有添加对映射完成后不保存上下文的特殊支持(它仍然是自动完成的)。不过,RestKit 创建和管理 Core Data 的方式已经改变。您仍然可以在 Core Data 之外创建对象,然后在准备好保存时将它们映射到托管对象中。试图篡改由 RestKit 创建的 Core Data 设置可能会在未来(如果不是立即)导致您出现问题,并且维护 2 个不同的持久存储可能比在 Core Data 之外准备数据然后在准备好时将其导入更复杂保存。
【讨论】:
所以,如果我需要手动保存到 CoreData,您的建议是使用“NSMutableDictionary”或“NSObjects”映射方法(如链接中指定)然后保存到 CoreData ?在这种情况下,我将不得不“手动”管理关系,但如果这是正确且更快的方式,我会接受您的回答。 就个人而言,我会重新审视您为什么要延迟保存,因为它会增加数据丢失的风险。如果必须,那么更快(风险更低)的开发路线确实是映射到字典/NSObject
,然后转换为 Core Data(您的 Core Data 模型类可以有方法来促进这一点)。
如果我没记错的话,ResKit 从 webService 读取 JSON,映射到 NSManagedObjects 并保存在 coreData 中,自动执行如下操作:更新现有记录,删除不再存在的记录并插入新记录.如果这是正确的,我的问题是当 JSON 以差异模式更新(服务器端)并且每次都没有返回所有记录时:我需要“手动”执行这些操作并在所有操作完成后执行保存到核心数据。如果我说错了,请纠正我。
RestKit 只会在您配置它时删除对象。此外,根据您的配置方式,它可能会从关系中删除项目。最后,你真的应该问你真正的问题——你不应该问你认为什么可以解决你的问题(尽管你应该把它加到你真正问题的末尾)......
这只是一个例子,我还处于 ResKit 的研究阶段,我只是想象了一个可以使用我提出的解决方案的例子。不管怎样,现在一切都清楚多了,我真的非常非常感谢你!以上是关于ResKit:临时 NSManagedObjects的主要内容,如果未能解决你的问题,请参考以下文章
为啥我们在 NSManagedObject 中需要临时 ID
如何在应用程序退出时正确删除“临时”NSManagedObject