NSURLSession

  • NSURLConnection在 iOS9 被宣布弃用,逐渐被 NSURLSession 替代;
  • NSURLSession 、 NSURLSessionConfiguration 、NSURLSessionTask 常用三个类;
  • AFNetWorking 从2.0版本开始,就是在 NSURLSession 的基础上封装的;

NSURLSession

使用:
1 - 通过NSURLSession的实例创建 task 任务;
2 - resume 执行 task 任务

NSURLSessionTask

可以理解为任务: 数据请求任务,下载任务,上传任务等;

  • NSURLSessionTask 的子类
NSURLSessionDataTask   数据请求
NSURLSessionUploadTask  上传
NSURLSessionDownloadTask  下载

NSURLSessionDataTask 数据请求任务

dataTask 是执行数据请求相关的任务,但也可以用来执行上传和下载相关的任务,是我们使用最多的task;

  • block 形式
    简单的get请求:
    如果返回值比较简单,则用这种简单的block方式。
NSURLSession *session = [NSURLSession sharedSession]; //单例创建session对象
NSURL *url = [NSURL URLWithString: "http://www.baidu.com/signin?username=13800138008&password=123456"];
// 初始化task
NSURLSessionTask *task = [session dataTaskWithURL:url completionHandler:^(NSData *data, NSURLResponse *response, NSError error) { 
   //数据处理
 NSLog(@"%@", [NSJSONSerialization JSONObjectWithData:data options:kNilOptions error:nil]);
}];
[task resume]; // 启动任务 :所有类型的task都要调用resume方法才会开始进行请求

简单的post请求:

NSURLSession *session = [NSURLSession sharedSession];

NSURL *url = [NSURL URLWithString: @"http://www.baidu.com/signin"];
NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL:url];
request.HTTPMethod = @"POST"; //post请求
request.HTTPBody = [@"username=13800138008&password=123456" dataUsingEncoding: 
NSUTF8StringEncoding];

// 通过request初始化task
NSURLSessionTask *task = [session dataTaskWithRequest:request completionHandler:^(NSData *data, NSURLResponse *response, NSError *error) { 
    NSLog(@"%@", [NSJSONSerialization JSONObjectWithData:data options:kNilOptions error:nil]); 
}];
[task resume];

get 和 post 的区别:

请求方式 初始化task 参数方式
get url 参数拼接在 urlString 后面
post request 将参数通过 utf8 编码,然后放在request 的body中
  • NSURLSessionDataDelegate 代理形式
    简单的数据可以用 block 的方式进行处理,如果返回的数据比较复杂,或者相对数据进一步处理,则使用 NSURLSession 的 delegate。
    delegate 分几个阶段 : 响应,接收数据,请求完成;
    以get为例:
//创建session: session的delegate属性是只读的;delegateQueue 表示代理方法在哪个队列中执行;
[NSURLSessionConfiguration defaultSessionConfiguration] 表示默认配置

NSURLSession *session = [NSURLSession sessionWithConfiguration:[NSURLSessionConfiguration defaultSessionConfiguration] delegate:self delegateQueue:[[NSOperationQueue alloc] init]];

// 创建任务
NSURLSessionDataTask *task = [session dataTaskWithRequest:[NSURLRequest requestWithURL:[NSURL URLWithString:@"http://www.baidu.com/login?userName=13800138008&password=123456"]]];

[task resume];  // 启动任务

delegate方法:

// 接收到服务器的响应
- (void)URLSession:(NSURLSession *)session dataTask:(NSURLSessionDataTask *)dataTask didReceiveResponse:(NSURLResponse *)response completionHandler:(void (^)(NSURLSessionResponseDisposition))completionHandler {

    completionHandler(NSURLSessionResponseAllow); // 允许处理服务器的响应,才会继续接收服务器返回的数据
}

// 接收服务器的数据(会调用多次)
- (void)URLSession:(NSURLSession *)session dataTask:(NSURLSessionDataTask *)dataTask didReceiveData:(NSData *)data {
    // 处理接收到的数据
}

// 请求完成
- (void)URLSession:(NSURLSession *)session task:(NSURLSessionTask *)task 
   didCompleteWithError:(NSError *)error {
    // 请求完成,处理成功的数据或者拿到错误的error值
}

NSURLSessionDownloadTask 下载任务

和 一样,有通过 url 和 request 两种方式来初始化 session;

  • 通过 url 来初始化,bloc形式:
SURLSession *session = [NSURLSession sharedSession];
NSURL *url = [NSURL URLWithString:@"http://www.baidu.com/source/icon/my.png"] ;

NSURLSessionDownloadTask *task = [session downloadTaskWithURL:url completionHandler:^(NSURL *location, NSURLResponse *response, NSError *error) {

    // 返回的  location 是沙盒中tmp文件夹下的一个临时url,文件下载后会存到这个位置,由于tmp中的文件随时可能被删除,所以我们需要自己需要把下载的文件挪到需要的地方
    NSString *path = [[NSSearchPathForDirectoriesInDomains(NSCachesDirectory, NSUserDomainMask,YES) lastObject] stringByAppendingPathComponent: response.suggestedFilename];

    // 移动文件; response.suggestedFilename 是 url 中的最后一部分,如:my.png
    [[NSFileManager defaultManager] moveItemAtURL:location toURL:[NSURL fileURLWithPath:path] 
      error:nil];
}];
[task resume]; // 启动任务
  • NSURLSessionDownloadDelegate 代理的形式:
// 每次写入调用(会调用多次)
- (void)URLSession:(NSURLSession *)session downloadTask:(NSURLSessionDownloadTask *)downloadTask didWriteData:(int64_t)bytesWritten totalBytesWritten:(int64_t)totalBytesWritten totalBytesExpectedToWrite:(int64_t)totalBytesExpectedToWrite {
   // 可在这里通过已写入的长度和总长度算出下载进度
   CGFloat progress = 1.0 * totalBytesWritten / totalBytesExpectedToWrite;
NSLog(@"%f",progress);
}

// 下载完成调用
- (void)URLSession:(NSURLSession *)session downloadTask:(NSURLSessionDownloadTask *)downloadTask didFinishDownloadingToURL:(NSURL *)location {

    // location 还是一个临时路径,需要自己挪到需要的路径(caches下面)
    NSString *filePath = [[NSSearchPathForDirectoriesInDomains(NSCachesDirectory, NSUserDomainMask,YES) lastObject] stringByAppendingPathComponent:downloadTask.response.suggestedFilename];
   //移动文件
    [[NSFileManager defaultManager] moveItemAtURL:location toURL:[NSURL fileURLWithPath:filePath] error:nil];
}

// 任务完成调用
- (void)URLSession:(NSURLSession *)session task:(NSURLSessionTask *)task didCompleteWithError:(NSError *)error {

}
  • 断点下载
    这种断点下载只支持应用内断点,如果程序在下载过程中途关闭,则不能恢复下载。
// 取消下载 :用这种方式取消下载,可以得到将来用来恢复的数据,保存起来
[self.task cancelByProducingResumeData:^(NSData *resumeData) {
    self.resumeData = resumeData; //保存数据
}];

// 下载失败导致的下载中断会进入此协议方法,也可以得到用来恢复的数据
- (void)URLSession:(NSURLSession *)session task:(NSURLSessionTask *)task didCompleteWithError:(NSError *)error {
    // 保存恢复数据
    self.resumeData = error.userInfo[NSURLSessionDownloadTaskResumeData];
}
// 恢复下载时接过保存的恢复数据
self.task = [self.session downloadTaskWithResumeData:self.resumeData];
[self.task resume];  // 启动任务

NSURLSessionUploadTask 上传任务

上传方式有两种:
1 -

NSURLSessionUploadTask *task = [[NSURLSession sharedSession] uploadTaskWithRequest:request fromFile:fileName completionHandler:^(NSData *data, NSURLResponse *response, NSError *error) {
}];

2 - post 方法: body 参数需要填写request的请求体(http协议规定格式的大长串)
出于安全考虑,用这种方法比较多;

[self.session uploadTaskWithRequest:request fromData: body completionHandler:^(NSData *data, NSURLResponse *response, NSError *error) {
    NSLog(@"%@", [NSJSONSerialization JSONObjectWithData:data options:kNilOptions error:nil]);
 }];

每个task 自身有都拥有下面几个方法

- (void)suspend;  暂停当前任务
- (void)resume;   启动任务,也可以唤醒suspend状态的任务
- (void)cancel;   取消当前的任务,也可以向处于suspend状态的任务发送cancel消息,任务如果被取消便不能再恢复到之前的状态。

NSURLSessionConfiguration 配置

  • 默认配置
NSURLSessionConfiguration *config = [NSURLSessionConfiguration defaultSessionConfiguration]; 
config.timeoutIntervalForRequest = 10; // 超时时间
config.allowsCellularAccess = YES; // 是否允许使用蜂窝网络(后台传输不适用)
  • task有三种配置
+ (NSURLSessionConfiguration *)defaultSessionConfiguration;   默认模式,会将缓存存储在磁盘上
+ (NSURLSessionConfiguration *)ephemeralSessionConfiguration;  瞬时会话模式,不会创建持久性存储的缓存
+ (NSURLSessionConfiguration *)backgroundSessionConfigurationWithIdentifier:(NSString *)identifier;后台会话模式,允许程序在后台进行上传下载工作

你可能感兴趣的:(NSURLSession)