afn text html,iOS网络请求AFNetworking "Request failed: unacceptable content-type: text/html"

科普 ContentType

Content-Type,内容类型,一般是指网页中存在的Content-Type,用于定义网络文件的类型和网页的编码,决定浏览器将以什么形式、什么编码读取这个文件与内容,这就是经常看到一些网页点击的结果却是下载到的一个文件或一张图片的原因。

73c9e07cecf48cc73bdb8a09e63935b2.png

requestSerializer与responseSerializer

7f006e89a3ad33e23cb94b80de95be35.png

requestSerializer

简单的来说AFNetworking的requestSerializer是决定AFNetworking以何种方式格式化序列化数据(即parameters,我们通常传一个字典)去请求api。

最终后台接收到的并不是我们认为的iOS中的一个字典parameters,或一个数组parameters

AFNetworking框架自动的将其格式化序列化成JSON、XML、等等文本格式,编码后放到HTTP请求的Body中,最后由后台API接收到。

请求的数据编码格式

而AFNetworking请求的数据编码格式又以下几种:

AFHTTPRequestSerializer      二进制

AFJSONRequestSerializer    JSON

AFPropertyListRequestSerializer   Plist

responseSerializer

简单的来说AFNetworking的responseSerializer是决定以何种方式格式化后台API响应返回的数据。

理论上完整的HTTP响应结束后,AFNetworking收到的并不是一个字典responseObject,或一个数组responseObject对象。而是字符串或者二进制数据。

AFNetworking框架自动的将HTTP响应回来的字符串数据(JSON、XML、二进制),反序列化解析成了APP端的对象,最终反回了responseObject对象。

响应的数据解码格式

AFHTTPResponseSerializer               二进制

AFJSONResponseSerializer              JSON

AFPropertyListResponseSerializer    Plist

AFXMLParserResponseSerializer      XML

AFImageResponseSerializer             Image

AFCompoundResponseSerializer      组合的

unacceptable content-type

com.alamofire.serialization.response.error.data=<5b7b2273 74617475 73223a22 73756363 65737322 2c226d73 67223a22 e799bbe9 9986e688 90e58a9f 227d5d>, NSLocalizedDescription=Request failed: unacceptable content-type: text/html}

AFNetworking请求API遇到这个问题的原因是,HTTP响应头中的 Content-Type 与返回数据的格式不一致导致的

比如常常后台API认为返回的是JSON编码的数据,虽然看似是JSON格式没错,但其实Content-Type并不是对应的JSON类型,这会导致客户端,即AFNetworking认为返回的数据是无效的数据,从而报错。

一个方法就是后台webservice更改返回数据的Content-Type为正确的application/json和text/json

如果后端某些原因无法更改,iOS客户端可以强制把未识别的 text/html类型加到AFNetworking可识别的列表中:

Objective-C

//_sharedClient为AFHTTPRequestOperationManager或者AFHTTPSessionManager的实例对象

_sharedClient.responseSerializer.acceptableContentTypes = [NSSet setWithObjects:@"application/json", @"text/json", @"text/javascript",@"text/html", @"text/plain",nil];

1

2

//_sharedClient为AFHTTPRequestOperationManager或者AFHTTPSessionManager的实例对象

_sharedClient.responseSerializer.acceptableContentTypes=[NSSetsetWithObjects:@"application/json",@"text/json",@"text/javascript",@"text/html",@"text/plain",nil];

acceptableContentTypes 为NSSet,如果缺后台对应的Content-type,可以直接添加进去

或者用更稳妥的方法,原有基础上追加Content-type

Objective-C

_sharedClient.responseSerializer.acceptableContentTypes = [_sharedClient.responseSerializer.acceptableContentTypes setByAddingObjectsFromSet:[NSSet setWithObjects:@"application/json", @"text/json", @"text/javascript",@"text/html", @"text/plain",@"application/atom+xml",@"application/xml",@"text/xml",@"image/png",@"image/jpeg",nil]];

1

_sharedClient.responseSerializer.acceptableContentTypes=[_sharedClient.responseSerializer.acceptableContentTypessetByAddingObjectsFromSet:[NSSetsetWithObjects:@"application/json",@"text/json",@"text/javascript",@"text/html",@"text/plain",@"application/atom+xml",@"application/xml",@"text/xml",@"image/png",@"image/jpeg",nil]];

一个完整AFNetworking示例

Objective-C

+ (NSURLSessionDataTask *)X_POST:(NSString *)URLString

parameters:(id)parameters

success:(void (^)(id responseObject))success

failure:(void (^)(NSError *error))failure{

AFHTTPSessionManager *manager = [AFHTTPSessionManager manager];

//发送json数据 {"key":"value","key2":"value2"}

manager.requestSerializer = [AFJSONRequestSerializer serializer];

//响应json数据

manager.responseSerializer = [AFJSONResponseSerializer serializer];

发送二进制form数据 key=value&key2=value2

//manager.requestSerializer = [AFHTTPRequestSerializer serializer];

响应二进制form数据

//manager.responseSerializer = [AFHTTPResponseSerializer serializer];

//直接发送JSON给服务器端 对应[AFJSONRequestSerializer serializer];

//实际httpbody中的数据为 {"name":"sky","password":"fox"}

NSDictionary *parametersDemo = @{@"name":@"sky",@"password":@"fox"};

将请求参数转换为JSON后放入key为aJSON的字典中发送请求 对应[AFHTTPRequestSerializer serializer];

实际httpbody中的数据为 {"aJSON":"{"name":"sky","password":"fox"}","key":"value"}

// NSDictionary *parametersJSON = @{@"name":@"sky",@"password":@"fox"};

//NSData *JSONData = [NSJSONSerialization dataWithJSONObject:self options:NSJSONWritingPrettyPrinted error:nil];

//NSString *JSONString = [[NSString alloc] initWithData:parametersJSON encoding:NSUTF8StringEncoding];

//NSMutableDictionary *parametersDemo = @{@"aJSON":JSONString?:@"",@"key":@"value"};

manager.responseSerializer.acceptableContentTypes = [manager.responseSerializer.acceptableContentTypes setByAddingObjectsFromSet:[NSSet setWithObjects:@"application/json", @"text/json", @"text/javascript",@"text/html", @"text/plain",@"application/atom+xml",@"application/xml",@"text/xml",nil]];

return [manager POST:URLString parameters:parametersDemo progress:^(NSProgress * _Nonnull uploadProgress) {

} success:^(NSURLSessionDataTask * _Nonnull task, id _Nullable responseObject) {

success(responseObject);

} failure:^(NSURLSessionDataTask * _Nullable task, NSError * _Nonnull error) {

NSString *responseString = [[NSString alloc] initWithData:(NSData *)error.userInfo[AFNetworkingOperationFailingURLResponseDataErrorKey] encoding:NSUTF8StringEncoding];

NSLog(@"%@",responseString);

failure(error);

}];

}

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

34

35

36

37

38

+(NSURLSessionDataTask*)X_POST:(NSString*)URLString

parameters:(id)parameters

success:(void(^)(idresponseObject))success

failure:(void(^)(NSError*error))failure{

AFHTTPSessionManager*manager=[AFHTTPSessionManagermanager];

//发送json数据  {"key":"value","key2":"value2"}

manager.requestSerializer=[AFJSONRequestSerializerserializer];

//响应json数据

manager.responseSerializer=[AFJSONResponseSerializerserializer];

发送二进制form数据 key=value&key2=value2

//manager.requestSerializer = [AFHTTPRequestSerializer serializer];

响应二进制form数据

//manager.responseSerializer  = [AFHTTPResponseSerializer serializer];

//直接发送JSON给服务器端   对应[AFJSONRequestSerializer serializer];

//实际httpbody中的数据为 {"name":"sky","password":"fox"}

NSDictionary*parametersDemo=@{@"name":@"sky",@"password":@"fox"};

将请求参数转换为JSON后放入key为aJSON的字典中发送请求    对应[AFHTTPRequestSerializer serializer];

实际httpbody中的数据为  {"aJSON":"{"name":"sky","password":"fox"}","key":"value"}

// NSDictionary *parametersJSON = @{@"name":@"sky",@"password":@"fox"};

//NSData *JSONData = [NSJSONSerialization dataWithJSONObject:self options:NSJSONWritingPrettyPrinted error:nil];

//NSString *JSONString = [[NSString alloc] initWithData:parametersJSON encoding:NSUTF8StringEncoding];

//NSMutableDictionary *parametersDemo = @{@"aJSON":JSONString?:@"",@"key":@"value"};

manager.responseSerializer.acceptableContentTypes=[manager.responseSerializer.acceptableContentTypessetByAddingObjectsFromSet:[NSSetsetWithObjects:@"application/json",@"text/json",@"text/javascript",@"text/html",@"text/plain",@"application/atom+xml",@"application/xml",@"text/xml",nil]];

return[managerPOST:URLStringparameters:parametersDemoprogress:^(NSProgress*_NonnulluploadProgress){

}success:^(NSURLSessionDataTask*_Nonnulltask,id_NullableresponseObject){

success(responseObject);

}failure:^(NSURLSessionDataTask*_Nullabletask,NSError*_Nonnullerror){

NSString*responseString=[[NSStringalloc]initWithData:(NSData*)error.userInfo[AFNetworkingOperationFailingURLResponseDataErrorKey]encoding:NSUTF8StringEncoding];

NSLog(@"%@",responseString);

failure(error);

}];

}

所有的ContentTypes都包含在http://www.iana.org/assignments/media-types/media-types.xhtml中

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值