Restkit 动态属性映射

Posted

技术标签:

【中文标题】Restkit 动态属性映射【英文标题】:Restkit Dynamic Attribute Mapping 【发布时间】:2013-10-11 01:36:48 【问题描述】:

我正在使用 RestKit v0.21 并尝试使用动态名称映射一组值。我能够正确获取自定义字段的名称,但无法捕获关联的值。 JSON 如下所示:


    "id": 1,
    "firstName": "Kenny",
    "lastName": "Powers",
    "customFields": 
        "favorite color": "blue",
        "hometown": "Cleveland",
        "spouse name": "sally"
    

我的映射如下所示:

//PERSON MAPPING
RKEntityMapping *personMapping = [RKEntityMapping mappingForEntityForName:@"Person" inManagedObjectStore:[RKManagedObjectStore defaultStore]];
[personMapping addAttributeMappingsFromDictionary:@
                                                     @"id":             @"personId",
                                                     @"firstName":      @"firstName",
                                                     @"lastName":       @"lastName"];
personMapping.identificationAttributes = @[ @"personId" ];

//CUSTOM FIELD MAPPING
RKEntityMapping *customFieldMapping = [RKEntityMapping mappingForEntityForName:@"CustomValue" inManagedObjectStore:[RKManagedObjectStore defaultStore]];
customFieldMapping.forceCollectionMapping = YES;
[customFieldMapping addAttributeMappingFromKeyOfRepresentationToAttribute:@"fieldName"];
[customFieldMapping addPropertyMapping:[RKAttributeMapping attributeMappingFromKeyPath:@"(fieldName)" toKeyPath:@"fieldValue"]];

[personMapping addPropertyMapping:[RKRelationshipMapping relationshipMappingFromKeyPath:@"customFields"
                                                                             toKeyPath:@"customValues"
                                                                           withMapping:customFieldMapping]];

我看到的所有动态属性示例都涉及值对象,其中值映射类似于“(fileName).email”。在我的情况下,它始终只是一个字符串:字符串名称和值的集合,代表一组完全动态的自定义字段和伴随值。

当我检查自定义字段对象的集合时,设置了 fieldName 属性,但 fieldValue 属性全部为 (null)。

有什么想法吗?

更新:这是自定义字段数组中元素的映射之一的日志输出:

2013-10-11 09:54:45.558 MyMobile[45460:6207] D restkit.object_mapping:RKMappingOperation.m:851 Starting mapping operation...
2013-10-11 09:54:45.558 MyMobile[45460:6207] T restkit.object_mapping:RKMappingOperation.m:852 Performing mapping operation: <RKMappingOperation 0x17a71230> for 'CustomValue' object. Mapping values from object 
    "Youtube Link" = "http://www.youtube.com";
 to object <CustomValue: 0xac42b00> (entity: CustomValue; id: 0xac69420 <x-coredata://D54F8070-D653-49E2-AFD5-90CD9778B2D4/CustomValue/p3> ; data: 
    fieldName = "Youtube Link";
    fieldValue = nil;
    person = "0x16f8d200 <x-coredata://D54F8070-D653-49E2-AFD5-90CD9778B2D4/Person/p389>";
) with object mapping (null)
2013-10-11 09:54:45.559 MyMobile[45460:6207] D restkit.object_mapping:RKMappingOperation.m:813 Found nested mapping definition to attribute 'fieldName'
2013-10-11 09:54:45.560 MyMobile[45460:6207] D restkit.object_mapping:RKMappingOperation.m:816 Found nesting value of 'Youtube Link' for attribute 'fieldName'
2013-10-11 09:54:45.562 MyMobile[45460:6207] T restkit.object_mapping:RKMappingOperation.m:440 Mapping attribute value keyPath '<RK_NESTING_ATTRIBUTE>' to 'fieldName'
2013-10-11 09:54:45.562 MyMobile[45460:6207] T restkit.object_mapping:RKMappingOperation.m:429 Found transformable value at keyPath '<RK_NESTING_ATTRIBUTE>'. Transforming from class '__NSCFString' to 'NSString'
2013-10-11 09:54:45.563 MyMobile[45460:6207] T restkit.object_mapping:RKMappingOperation.m:475 Skipped mapping of attribute value from keyPath '<RK_NESTING_ATTRIBUTE> to keyPath 'fieldName' -- value is unchanged (Youtube Link)
2013-10-11 09:54:45.564 MyMobile[45460:6207] T restkit.object_mapping:RKMappingOperation.m:497 Skipping attribute mapping for special keyPath '<RK_NESTING_ATTRIBUTE>'
2013-10-11 09:54:45.564 MyMobile[45460:6207] T restkit.object_mapping:RKMappingOperation.m:440 Mapping attribute value keyPath 'Youtube Link' to 'fieldValue'
2013-10-11 09:54:45.565 MyMobile[45460:6207] T restkit.object_mapping:RKMappingOperation.m:429 Found transformable value at keyPath 'Youtube Link'. Transforming from class '__NSCFString' to 'NSString'
2013-10-11 09:54:45.565 MyMobile[45460:6207] E restkit.object_mapping:RKMappingOperation.m:431 Failed transformation of value at keyPath 'Youtube Link' to representation of type 'NSString': (null)
2013-10-11 09:54:45.566 MyMobile[45460:6207] D restkit.object_mapping:RKMappingOperation.m:920 Finished mapping operation successfully...

【问题讨论】:

不知道它是否有效,但您可以尝试attributeMappingFromKeyPath:nil toKeyPath:@"fieldValue"。需要逐步完成映射过程以查看可用的数据... 我试过了:[customFieldMapping addPropertyMapping:[RKAttributeMapping attributeMappingFromKeyPath:nil toKeyPath:@"fieldValue"]]; 但这并没有太大的区别。单步执行时,映射过程的源代码中的何处是一个好地方? 打开映射的跟踪日志并通过RKMappingOperation.m进行调试 我用日志详细信息更新了我的原始问题。有什么突然出现在你身上吗? 并非如此。我不确定您是否可以直接使用映射来做到这一点。 RestKit API 基于将字典中的每个未知键提取到单个对象中。我认为是强制集合映射将所有内容混合在一起。 【参考方案1】:

我最近遇到了类似的问题。使用动态属性映射时,有时值转换器似乎未正确初始化。

我找到了一种解决方法,方法是在我的 NSManagedObject 子类中将属性从 NSString 更改为类型 id。例如,假设您的 NSManagedObject 通常看起来像这样:

@interface CustomValue : NSManagedObject

@property (nonatomic, retain) NSString * fieldValue;

@end

尝试将其更改为:

@interface CustomValue : NSManagedObject

@property (nonatomic, retain) id fieldValue;

@end

您还必须将数据模型中的 fieldValueString 更改为 Transformable

我这样做后,映射仍然将类型转换为NSString,但它成功了。

【讨论】:

以上是关于Restkit 动态属性映射的主要内容,如果未能解决你的问题,请参考以下文章

使用 RestKit 处理多级动态嵌套属性

RestKit 对象建模动态数据

RestKit 0.20:restkit 对象映射使属性映射加倍

RestKit 0.20:映射复杂的动态嵌套 JSON

RestKit 的动态映射会解决这个复杂的 JSON 映射吗?

RestKit - 实体映射属性转换