AFNetworking 500 response body

前端 未结 3 1915
野的像风
野的像风 2021-01-02 13:17

I\'ve been using AFNetworking 2.0 in my app. I\'ve noticed that if my web-service returns a 500 status code I do not get the body of the response.

Here is an example

相关标签:
3条回答
  • 2021-01-02 13:47

    UPDATE: I have created a github repository to contain the latest code I am using. All changes will be posted there. https://github.com/Hackmodford/HMFJSONResponseSerializerWithData

    The answer comes from this issue on github. https://github.com/AFNetworking/AFNetworking/issues/1397

    gfiumara is the dev who came up with this. I have only slightly modified his subclass of AFJSONResponseSerializer to include an actual string instead of the NSData

    //MSJSONResponseSerializerWithData.h
    
    #import "AFURLResponseSerialization.h"
    
    /// NSError userInfo key that will contain response data
    static NSString * const JSONResponseSerializerWithDataKey = @"JSONResponseSerializerWithDataKey";
    
    @interface MSJSONResponseSerializerWithData : AFJSONResponseSerializer
    
    @end
    

    //  MSJSONResponseSerializerWithData.m
    
    #import "MSJSONResponseSerializerWithData.h"
    
    @implementation MSJSONResponseSerializerWithData
    
    - (id)responseObjectForResponse:(NSURLResponse *)response
                               data:(NSData *)data
                              error:(NSError *__autoreleasing *)error
    {
        if (![self validateResponse:(NSHTTPURLResponse *)response data:data error:error]) {
            if (*error != nil) {
                NSMutableDictionary *userInfo = [(*error).userInfo mutableCopy];
                userInfo[JSONResponseSerializerWithDataKey] = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];
                NSError *newError = [NSError errorWithDomain:(*error).domain code:(*error).code userInfo:userInfo];
                (*error) = newError;
            }
    
            return (nil);
        }
    
        return ([super responseObjectForResponse:response data:data error:error]);
    }
    
    @end
    

    Here is an example of how I use it in the failure block.

    } failure:^(NSURLSessionDataTask *task, NSError *error) {
            NSLog(@"%@",[error.userInfo objectForKey:@"JSONResponseSerializerWithDataKey"]); 
        }];
    
    0 讨论(0)
  • 2021-01-02 13:52

    You need to use AFCompoundSerializer to tell the AFNetworking framework how to process all of the possible responses it could receive. By default it will only try to map JSON. A compound serializer will work through the serializers until it finds one that doesn't raise an error.


    You want to use:

    + (instancetype)compoundSerializerWithResponseSerializers:(NSArray *)responseSerializers
    

    on AFCompoundResponseSerializer (in AFURLResponseSerialization.h).

    You need to pass an array of serializers that can handle the response. One of the serializers in the array should be an instance of AFHTTPResponseSerializer to handle your error responses.

    0 讨论(0)
  • 2021-01-02 14:01

    If you include my category in your project, it's as simple as the following:

    [mySessionManager POST:@"some-api" parameters:params success:^(NSURLSessionDataTask *task, NSDictionary *responseObject) {
        ...
    } failure:^(NSURLSessionDataTask *task, NSError *error) {
        id responseObject = error.userInfo[kErrorResponseObjectKey];
        ... do something with the response ...
    }];
    

    Here's the code for my category. It swizzles AFURLSessionManager to inject a shim into the completion handler. The shim puts the response into the NSError's userInfo.

    https://gist.github.com/chrishulbert/35ecbec4b37d36b0d608

    0 讨论(0)
提交回复
热议问题