AFN的简单使用
2017-03-06 本文已影响475人
MiracleGl
AFNetworking是一个令人愉快的iOS和Mac OS X的网络库。它建立在基础URL加载系统之上,扩展了Cocoa中内置的强大的高级网络抽象。它有一个模块化架构,设计良好,功能丰富的API,使用起来很方便。
- AFN的简介
- 简介
- 请求数据格式
- 响应数据格式
- 数据格式小结
- AFN模拟登陆
- 发送GET请求获取普通的Json数据
- AFN发送GET请求模拟登陆
- AFN发送POST请求模拟登陆
- AFN常见错误
- AFN实现文件上传和下载
- 文件上传
- 文件下载
- AFN常用功能
- AFN之BaseURL
- AFN之HTTPS
- AFN之监测网络环境
- 封装简单的网络请求工具类
AFN的简介
简介
- 目前国内开发网络应用使用最多的第三方框架
- 是专为
Mac OS
和iOS
设计的一套网络框架 - 对
NSURLConnection
和NSURLSession
做了封装 - 提供有丰富的API
- 提供了完善的错误解决方案
- 使用起来相对来说比较简单
- 官网地址:AFNetworking
请求数据格式
AFURLRequestSerialization
| 类型 | 说明 |
| --- | :---: | ---:|
| AFHTTPRequestSerializer
| 二进制的,默认的 |
| AFJSONRequestSerializer
| JSON(POST JSON) RESTful 设计风格需要 |
| AFPropertyListRequestSerializer
| PList(POST Plist-开发中几乎不用) |
响应数据格式
AFURLResponseSerialization
| 类型 | 说明 |
| --- | :---: | ---:|
| AFHTTPResponseSerializer
| HTTP二进制的 |
| AFJSONResponseSerializer
| JSON默认的 |
| AFXMLParserResponseSerializer
| XML Parser解析器 SAX解析 |
| AFXMLDocumentResponseSerializer
| (Mac OS X) XML DOM |
| AFPropertyListResponseSerializer
| PList几乎不用 |
| AFImageResponseSerializer
| 图像,不支持GIF |
| AFCompoundResponseSerializer
| 组合的 |
数据格式小结
- 大多数情况下,都是
JSON
格式,不需要指定 - 如果是
XML
格式- 如果
SAX
解析,需要指定格式manager.responseSerializer = [AFXMLParserResponseSerializer serializer];
- 然后利用代理方法解析
- 如果
DOM
解析,需要指定格式manager.responseSerializer = [AFHTTPResponseSerializer serializer];
- 然后利用第三方框架解析
- 如果
- 图像
-
AFN
支持图像缓存 - 但是不支持
GIF
-
- 提示
- 使用
AFN
时,一定记住要输出:error
- 使用
AFN模拟登陆
导入头文件:
#import "AFNetworking.h
发送GET请求获取普通的JSON数据
- (IBAction)demo:(id)sender
{
// 1.网络请求地址
NSString *URLString = @"http://xxxx/demo.json";
// 2.创建网络请求管理者
AFHTTPSessionManager *manager = [AFHTTPSessionManager manager];
// 3.发送网络请求
[manager GET:URLString parameters:nil progress:nil success:^(NSURLSessionDataTask * _Nonnull task, id _Nullable responseObject) {
NSLog(@"%@ %@",[responseObject class],responseObject);
} failure:^(NSURLSessionDataTask * _Nullable task, NSError * _Nonnull error) {
NSLog(@"%@",error);
}];
}
AFN发送GET请求模拟登陆
- (IBAction)GETLogin:(id)sender {
// NSString *URLString = @"http://xxxx/php/login/login.php?username=zhangsan&password=zhang";
// 登陆地址
NSString *URLString = @"http://xxxx/php/login/login.php";
// 网络请求管理者
AFHTTPSessionManager *manager = [AFHTTPSessionManager manager];
// 请求参数
NSMutableDictionary *parameters = [NSMutableDictionary dictionary];
parameters[@"username"] = @"zhangsan";
parameters[@"password"] = @"zhang";
// 发送GET请求
[manager GET:URLString parameters:parameters progress:nil success:^(NSURLSessionDataTask * _Nonnull task, id _Nullable responseObject) {
NSLog(@"%@",responseObject);
} failure:^(NSURLSessionDataTask * _Nullable task, NSError * _Nonnull error) {
NSLog(@"%@",error);
}];
}
AFN发送POST请求模拟登陆
- (IBAction)POSTLogin:(id)sender {
// 登陆地址
NSString *URLString = @"http://xxxx/php/login/login.php";
// 网络请求管理者
AFHTTPSessionManager *manager = [AFHTTPSessionManager manager];
// 请求参数
NSMutableDictionary *parameters = [NSMutableDictionary dictionary];
parameters[@"username"] = @"zhangsan";
parameters[@"password"] = @"zhang";
// 发送POST请求
[manager POST:URLString parameters:parameters progress:nil success:^(NSURLSessionDataTask * _Nonnull task, id _Nullable responseObject) {
NSLog(@"%@",responseObject);
} failure:^(NSURLSessionDataTask * _Nullable task, NSError * _Nonnull error) {
NSLog(@"%@",error);
}];
}
AFN常见错误
AFN常见的序列化和反序列化的错误
1.常见错误一 :
AFN支持接收 @"application/json", @"text/json", @"text/javascript" 文本类型
AFN不支持接收 text/html 文本类型
2.常见错误二 :
AFN默认的成功的回调 responseObject 是把服务器返回的数据当做JSON数据格式解析,返回字典或者数组.
但是在加载网页数据时,响应体是字符串.需要修改响应的序列化方式,让AFN给我们返回原始的二进制数据即可.
3.常见错误三 :
AFN不支持接收 text/plian 文本类型
4.常见错误四 :
AFN默认只支持向服务器发送普通的二进制数据.比如普通的GET和POST请求数据.默认不支持发送JSON数据到服务器
如果要向服务器发送JSON格式的二进制数据,就需要特殊的处理请求的方式.使AFN支持向服务器发送JSON形式的二进制数据
其他常见错误
- 加载网页数据时
- (void)loadData
{
// 网络请求manager
AFHTTPSessionManager *manager = [AFHTTPSessionManager manager];
// 常见错误一 : 修改AFN支持接收的文本类型 : text/html
manager.responseSerializer.acceptableContentTypes = [NSSet setWithObjects:@"application/json", @"text/json", @"text/javascript", @"text/html", nil];
// 常见错误二 : 修改AFN默认的返回的数据类型,设置默认为只返回原始的二进制数据,程序猿自己解析
manager.responseSerializer = [AFHTTPResponseSerializer serializer];
// 网络请求地址
NSString *URLStr = @"http://www.baidu.com";
// 发送网络请求
[manager GET:URLStr parameters:nil progress:nil success:^(NSURLSessionDataTask * _Nonnull task, id _Nullable responseObject) {
// NSLog(@"%@ %@",[responseObject class],responseObject);
NSString *html = [[NSString alloc] initWithData:responseObject encoding:NSUTF8StringEncoding];
NSLog(@"%@",html);
} failure:^(NSURLSessionDataTask * _Nullable task, NSError * _Nonnull error) {
NSLog(@"出错 %@",error);
}];
}
- 向服务器发送JSON数据时
- (void)postJSON
{
// 网络请求manager
AFHTTPSessionManager *manager = [AFHTTPSessionManager manager];
// 常见错误三 : 修改AFN支持接收的文本类型 : text/plian
manager.responseSerializer.acceptableContentTypes = [NSSet setWithObjects:@"application/json", @"text/json", @"text/javascript", @"text/html", @"text/plain", nil];
// 常见错误二 : 修改AFN默认的返回的数据类型,设置默认为只返回原始的二进制数据,程序猿自己解析
manager.responseSerializer = [AFHTTPResponseSerializer serializer];
// 常见错误四 : 修改AFN支持向服务器发送JSON形式的二进制数据
manager.requestSerializer = [AFJSONRequestSerializer serializer];
// 网络请求地址
NSString *URLStr = @"http://localhost/php/upload/postjson.php";
// 请求参数
NSDictionary *parameters = @{
@"name":@"zhangsan"
};
// 发送网络请求
[manager POST:URLStr parameters:parameters progress:nil success:^(NSURLSessionDataTask * _Nonnull task, id _Nullable responseObject) {
// NSLog(@"%@ %@",[responseObject class],responseObject);
NSString *html = [[NSString alloc] initWithData:responseObject encoding:NSUTF8StringEncoding];
NSLog(@"%@",html);
} failure:^(NSURLSessionDataTask * _Nullable task, NSError * _Nonnull error) {
NSLog(@"出错 %@",error);
}];
}
AFN实现文件上传和下载
文件上传
-
文件数据拼接的方法
[formData appendPartWithFileData:data name:@"" fileName:@"" mimeType:@""];
-
文件数据拼接的四个参数
- 参数1:上传文件的二进制信息
- 参数2:服务器接收二进制数据的字段名(跟服务器要)
- 参数3:文件保存到服务器的名字
- 参数4:上传的文件的类型
-
文件上传的主方法
- (void)uploadFile
{
// 网络请求地址
NSString *URLStr = @"http://xxxx/php/upload/upload-m.php";
// 文件上传的附带信息
NSDictionary *textDict = @{
@"status":@"zhangsan"
};
// 网络请求manager
AFHTTPSessionManager *manager = [AFHTTPSessionManager manager];
// 发送POST请求
[manager POST:URLStr parameters:textDict constructingBodyWithBlock:^(id<AFMultipartFormData> _Nonnull formData) {
// 获取文件路径1
NSString *filePath1 = [[NSBundle mainBundle] pathForResource:@"mm01.jpg" ofType:nil];
NSData *fileData1 = [NSData dataWithContentsOfFile:filePath1];
// 拼接数据1
[formData appendPartWithFileData:fileData1 name:@"userfile[]" fileName:[filePath1 lastPathComponent] mimeType:@"image/jpg"];
// 获取文件路径2
NSString *filePath2 = [[NSBundle mainBundle] pathForResource:@"mm02.jpg" ofType:nil];
NSData *fileData2 = [NSData dataWithContentsOfFile:filePath2];
// 拼接数据2
[formData appendPartWithFileData:fileData2 name:@"userfile[]" fileName:[filePath2 lastPathComponent] mimeType:@"image/jpg"];
} progress:^(NSProgress * _Nonnull uploadProgress) {
NSLog(@"进度 %f",uploadProgress.fractionCompleted);
} success:^(NSURLSessionDataTask * _Nonnull task, id _Nullable responseObject) {
NSLog(@"%@ %@",[responseObject class],responseObject);
} failure:^(NSURLSessionDataTask * _Nullable task, NSError * _Nonnull error) {
NSLog(@"出错 %@",error);
}];
}
文件下载
- (void)downloadFile
{
// 下载地址
NSString *URLString = @"http://xxxx/xcode.zip";
// 请求
NSURLRequest *request = [NSURLRequest requestWithURL:[NSURL URLWithString:URLString]];
// 管理者
AFHTTPSessionManager *manager = [AFHTTPSessionManager manager];
// 发起下载任务
NSURLSessionDownloadTask *downloadTask = [manager downloadTaskWithRequest:request progress:^(NSProgress * _Nonnull downloadProgress) {
NSLog(@"进度 %f",downloadProgress.fractionCompleted);
} destination:^NSURL * _Nonnull(NSURL * _Nonnull targetPath, NSURLResponse * _Nonnull response) {
// AFN提供的文件保存路径,在tmp文件中,下载完成之后就会被删除
NSLog(@"%@",targetPath);
// 自己获取文件保存的路径
NSString *filePath = [[NSSearchPathForDirectoriesInDomains(NSCachesDirectory, NSUserDomainMask, YES) lastObject] stringByAppendingPathComponent:response.suggestedFilename];
// 带file:// 协议头
NSURL *locationURL = [NSURL fileURLWithPath:filePath];
// 把文件缓存路径剪切出去
return locationURL;
} completionHandler:^(NSURLResponse * _Nonnull response, NSURL * _Nullable filePath, NSError * _Nullable error) {
// 文件最终保存的路径 : 从上面自动剪切过来的
NSLog(@"%@",filePath.path);
}];
// 开启下载任务
[downloadTask resume];
}
AFN其他常用功能
AFN之BaseURL
- 使用场景:设计网络请求工具类时使用
- (IBAction)baseURL:(id)sender
{
AFHTTPSessionManager *manager = [[AFHTTPSessionManager alloc] initWithBaseURL:[NSURL URLWithString:@"http://localhost/"]];
[manager GET:@"demo.json" parameters:nil progress:nil success:^(NSURLSessionDataTask * _Nonnull task, id _Nullable responseObject) {
NSLog(@"%@",responseObject);
} failure:^(NSURLSessionDataTask * _Nullable task, NSError * _Nonnull error) {
NSLog(@"%@",error);
}];
}
AFN之HTTPS
// 允许无效的证书 : 2.5.4 版本之前使用
manager.securityPolicy.allowInvalidCertificates = YES;
// 不验证域名 : 2.6.0 版本之后使用
manager.securityPolicy.validatesDomainName = NO;
- (IBAction)HTTPS:(id)sender
{
// 创建网络请求mansger
AFHTTPSessionManager *manager = [AFHTTPSessionManager manager];
// 允许无效的证书
// manager.securityPolicy.allowInvalidCertificates = YES;
// 不验证域名
manager.securityPolicy.validatesDomainName = NO;
// 修改AFN默认支持接收的文本类型
manager.responseSerializer.acceptableContentTypes = [NSSet setWithObjects:@"application/json", @"text/json", @"text/javascript", @"text/html" ,nil];
// 修改AFN默认处理数据的方式 : 设置成只返回原始的二进制数据,程序猿自己反序列化
manager.responseSerializer = [AFHTTPResponseSerializer serializer];
// 网络请求地址
NSString *URLStr = @"https://www.baidu.com";
[manager GET:URLStr parameters:nil progress:nil success:^(NSURLSessionDataTask * _Nonnull task, id _Nullable responseObject) {
// NSLog(@"%@ %@",[responseObject class],responseObject);
// 反序列化
NSString *html = [[NSString alloc] initWithData:responseObject encoding:NSUTF8StringEncoding];
NSLog(@"%@",html);
} failure:^(NSURLSessionDataTask * _Nullable task, NSError * _Nonnull error) {
NSLog(@"出错 %@",error);
}];
}
AFN之监测网络环境
- 程序一启动就开始监测网络环境
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
// Override point for customization after application launch.
// 监测网络环境
AFNetworkReachabilityManager *manager = [AFNetworkReachabilityManager sharedManager];
/*
status
AFNetworkReachabilityStatusUnknown = -1, 不知道监测的是什么
AFNetworkReachabilityStatusNotReachable = 0, 没有检测到网络
AFNetworkReachabilityStatusReachableViaWWAN = 1, 蜂窝网
AFNetworkReachabilityStatusReachableViaWiFi = 2, WIFI
*/
[manager setReachabilityStatusChangeBlock:^(AFNetworkReachabilityStatus status) {
NSLog(@"%zd",status);
}];
[manager startMonitoring];
return YES;
}
封装简单的网络请求工具类
新建类 NetworkTool
NetworkTool.h
// 第一步 : 继承自 AFHTTPSessionManager
@interface NetworkTool : AFHTTPSessionManager
/**
* 网络请求工具类全局访问点
*
* @return AFHTTPSessionManager的实例
*/
+ (instancetype)sharedNetworkTool;
/**
* 网络请求工具类GET请求的主方法
*
* @param URLString 请求地址
* @param success 成功的回调
* @param faile 失败的回调
*/
- (void)GETWithURLString:(NSString *)URLString success:(void(^)(id responseObject))success faile:(void(^)(NSError *error))faile;
NetworkTool.m
+ (instancetype)sharedNetworkTool
{
static NetworkTool *instance;
static dispatch_once_t onceToken;
dispatch_once(&onceToken, ^{
// 设置相对路径
NSURL *BaseURL = [NSURL URLWithString:@"http://c.m.163.com/nc/"];
// 实例化Manager
instance = [[self alloc] initWithBaseURL:BaseURL];
// 增加AFN支持的文件类型
instance.responseSerializer.acceptableContentTypes = [NSSet setWithObjects:@"application/json", @"text/json", @"text/javascript", @"text/html", @"text/plain", nil];
});
return instance;
}
// 网络工具类实现GET请求的主方法
- (void)GETWithURLString:(NSString *)URLString success:(void (^)(id))success faile:(void (^)(NSError *))faile
{
[self GET:URLString parameters:nil progress:nil success:^(NSURLSessionDataTask * _Nonnull task, id _Nullable responseObject) {
if (success) {
success(responseObject);
}
} failure:^(NSURLSessionDataTask * _Nullable task, NSError * _Nonnull error) {
if (faile) {
faile(error);
}
}];
}
感谢读到最后的朋友,最后祝大家工作顺利,请点赞支持一下,谢谢!