Restkit:multipartFormRequestWithObject 不是 json

Posted

技术标签:

【中文标题】Restkit:multipartFormRequestWithObject 不是 json【英文标题】:Restkit : multipartFormRequestWithObject not json 【发布时间】:2013-10-23 08:48:00 【问题描述】:

我正在使用 RestKit 2.0 通过“multipartFormRequestWithObject”方法将核心数据实体和图像发送到服务器。但是,当实体数据到达时,它不是 json 格式。如果我使用没有图像的“postObject”发送实体,则数据为 json 格式。我对这两种情况都使用相同的 RKObjectMapping。 我需要做什么才能使对象序列化为 json?我试过了

[request setValue:@"application/json" forHTTPHeaderField:@"content-type"]; 

但这并没有帮助,我已经有了我的对象管理器设置:

[objectManager setRequestSerializationMIMEType:RKMIMETypeJSON];
[objectManager setAcceptHeaderWithMIMEType:RKMIMETypeJSON];

我的 Header Content-Type 是 multipart/form-data 但我想这是必需的。

request.headers=
Accept = "application/json";
"Accept-Language" = "en;q=1, fr;q=0.9, de;q=0.8, zh-Hans;q=0.7, zh-Hant;q=0.6, ja;q=0.5";
"Accept-Version" = 1;
"Content-Length" = 19014;
"Content-Type" = "multipart/form-data; boundary=Boundary+0xAbCdEfGbOuNdArY";
"User-Agent" = "app/1.0 (iPhone Simulator; ios 7.0; Scale/2.00)";

我的完整代码用于映射和操作如下。像往常一样,任何反馈都会很棒。谢谢。铝

- (void)loginMainUser:(NSDictionary*)paramsDict path:(NSString *)apiPath

RKObjectManager *manager = [RKObjectManager sharedManager];

// Response Mapping
RKObjectMapping *mapping = [RKObjectMapping mappingForClass:[self class]];
[mapping addAttributeMappingsFromDictionary:@@"token" : @"token",
                                              @"_links" : @"links"];

[manager addResponseDescriptorsFromArray:@[[RKResponseDescriptor responseDescriptorWithMapping:mapping
                                                                                        method:RKRequestMethodAny
                                                                                   pathPattern:nil
                                                                                       keyPath:nil
                                                                                   statusCodes:RKStatusCodeIndexSetForClass(RKStatusCodeClassSuccessful)]]];
// Request Mapping
RKObjectMapping *userRequestMapping = [RKObjectMapping requestMapping];
[userRequestMapping addAttributeMappingsFromDictionary:@@"name" : @"first_name",
                                                         @"surname" : @"last_name",
                                                         @"email" : @"email",
                                                         @"password" : @"password"];

RKRequestDescriptor *requestDescriptor = [RKRequestDescriptor requestDescriptorWithMapping:userRequestMapping
                                                                               objectClass:[self class]
                                                                               rootKeyPath:nil
                                                                                    method:RKRequestMethodAny];
[manager addRequestDescriptor:requestDescriptor];


UIImage *image = [UIImage imageNamed:@"logo.png"];

// Serialize the Article attributes then attach a file
NSMutableURLRequest *request = [manager multipartFormRequestWithObject:self
                                                                method:RKRequestMethodPOST
                                                                  path:apiPath
                                                            parameters:nil
                                             constructingBodyWithBlock:^(id<AFMultipartFormData> formData) 
                                                 [formData appendPartWithFileData:UIImagePNGRepresentation(image)
                                                                             name:@"logo"
                                                                         fileName:@"logo.png"
                                                                        mimeType:@"image/png"];
                                                                     ];

RKObjectRequestOperation *operation = [manager objectRequestOperationWithRequest:request
                                                                         success:^(RKObjectRequestOperation *operation, RKMappingResult *mappingResult) 
                                                                             NSLog(@"Success");
                                                                          failure:^(RKObjectRequestOperation *operation, NSError *error) 
                                                                             NSLog(@"Failed");
                                                                         ];

[manager enqueueObjectRequestOperation:operation];

【问题讨论】:

你能解决这个问题吗?请分享,我面临着完全相同的问题。 是的,Wain 的回答帮助了我。我不记得确切的细节了,因为我无法再访问那个项目了。 【参考方案1】:

multipartFormRequestWithObject 明确不是 JSON。这是设计使然。更改的是 HTTP 内容类型,因此 JSON 和多部分形式是互斥的。

因此,您需要改变对要实现的目标的想法。

一种选择是使用映射操作为您的对象创建 JSON,然后在您调用 multipartFormRequestWithObject 时提供该 JSON。这将为您提供一个多部分表单消息,其中包含一段可以在服务器上反序列化的 JSON。

【讨论】:

【参考方案2】:

这不是最好的方法,但如果您确实需要使用 RestKit 从对象中获取 JSON,您可以使用以下代码对其进行转换:

// The object you want to convert
YourObject *object = ...;

// The RestKit descriptor that you want to use to map.
RKRequestDescriptor *requestDescriptorObject = ...;

NSDictionary *parametersForObject;
parametersForObject = [RKObjectParameterization parametersWithObject:object 
                                                   requestDescriptor:requestDescriptorObject 
                                                               error:nil];


NSData *jsonData = [NSJSONSerialization dataWithJSONObject:parametersForObject 
                                                   options:NSJSONWritingPrettyPrinted 
                                                     error:nil];


NSString *jsonString;
if(jsonData) 
    jsonString = [[NSString alloc] initWithData:jsonData 
                                       encoding:NSUTF8StringEncoding];

然后使用 JSON 字符串,您可以将其发布在多部分帖子中。可以使用任何方法完成,但由于您已经拥有 RestKit,因此您可以使用库来完成。

例如,在下面的代码中有一个文件和JSON字符串(实际上是JSON数据)的帖子。

 // The RestKit manager
 RKObjectManager *manager = ...;

 // The server endpoint
 NSString *path = ...;

 NSMutableURLRequest *request = [manager multipartFormRequestWithObject:nil method:RKRequestMethodPOST path:path parameters:nil constructingBodyWithBlock:^(id<AFMultipartFormData> formData) 
     // Post of the file
     [formData appendPartWithFileData:[NSData dataWithData:self.dataFile]
                                 name:@"file"
                             fileName:filename
                             mimeType:mimetype];

     // Post of the JSON data
     [formData appendPartWithFormData:jsonData name:@"json_data"];
 ];

【讨论】:

这会将 json 作为字符串而不是对象发送给我的后端以进行有效解析? (django) 有没有办法解决这个问题?

以上是关于Restkit:multipartFormRequestWithObject 不是 json的主要内容,如果未能解决你的问题,请参考以下文章

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

将“import <RestKit/RestKit.h>”添加到 AppDelegate.m 的问题

RestKit 与直接 CoreData

Restkit 0.20.x cocoapods 安装问题 - 编译但找不到 RestKit 的导入

RestKit / Core Data / Offline - 我需要 UUID 还是 RestKit 足够聪明?

RestKit 核心数据集成