iOS网络开发之NSURLSession学习<2>
2015-10-20 17:49
701 查看
这篇文章主要介绍了
一.
Task是由Session创建的,Session会保持对Task的一个强引用,直到Task完成或者出错才会释放。通过NSURLSessionTask可以获得Task的各种状态,以及对Task进行取消,挂起,继续等操作。一共包括三种Task,三种Task的结构如图。本文主要讲解的是DataTask。
![](http://img.blog.csdn.net/20151020165852186)
1.管理task的状态的方法
2.获得task的执行情况的属性
countOfBytesExpectedToReceive
countOfBytesReceivedcountOfBytesExpectedToSendcountOfBytesSent
3.task的综合信息
currentRequest // 当前活跃的request
originalRequest // 在task创建的时候传入的request(有可能会重定向)
response // 服务器对当前活跃请求的响应
taskDescription // 描述当前task
taskIdentifier// 用来区分Task的描述符
error //Task失败的错误信息
4.task状态的枚举
typedef NS_ENUM (NSInteger, NSURLSessionTaskState ) { NSURLSessionTaskStateRunning = 0, NSURLSessionTaskStateSuspended = 1, NSURLSessionTaskStateCanceling = 2, NSURLSessionTaskStateCompleted = 3,};
二.
DataTask是用来干嘛的呢? 用来下载数据到内存里,数据的格式是
dataTask使用的过程中,有两种方式来处理结果
通过block的方式(不关注过程,只关注结果,使用简单)
下载一幅图片,完成后显示到ImageView。代码:
通过代理方法来管理session和task。( 可以获得全部过程,但是较为复杂)
1.
2.
3.
代码示例:
NSURLSession以及
NSURLSessionTask这个抽象类,和
NSURLSessionDataTask的使用和代理方法。
一.
NSURLSessionTask的介绍
Task是由Session创建的,Session会保持对Task的一个强引用,直到Task完成或者出错才会释放。通过NSURLSessionTask可以获得Task的各种状态,以及对Task进行取消,挂起,继续等操作。一共包括三种Task,三种Task的结构如图。本文主要讲解的是DataTask。
1.管理task的状态的方法
-(void)cancel//取消一个task
-(void)resume//如果task在挂起状态,则继续执行task
(void)suspend//挂起task
2.获得task的执行情况的属性
countOfBytesExpectedToReceive
countOfBytesReceivedcountOfBytesExpectedToSendcountOfBytesSent
3.task的综合信息
currentRequest // 当前活跃的request
originalRequest // 在task创建的时候传入的request(有可能会重定向)
response // 服务器对当前活跃请求的响应
taskDescription // 描述当前task
taskIdentifier// 用来区分Task的描述符
error //Task失败的错误信息
4.task状态的枚举
typedef NS_ENUM (NSInteger, NSURLSessionTaskState ) { NSURLSessionTaskStateRunning = 0, NSURLSessionTaskStateSuspended = 1, NSURLSessionTaskStateCanceling = 2, NSURLSessionTaskStateCompleted = 3,};
二.
NSURLSessionDataTask代理
DataTask是用来干嘛的呢? 用来下载数据到内存里,数据的格式是
NSData。
dataTask使用的过程中,有两种方式来处理结果
通过block的方式(不关注过程,只关注结果,使用简单)
下载一幅图片,完成后显示到ImageView。代码:
NSURLSessionDataTask * task = [self.session dataTaskWithURL:[NSURL URLWithString:imageURL] completionHandler:^(NSData *data, NSURLResponse *response, NSError *error) { if (!error) { UIImage * image = [UIImage imageWithData:data]; self.imageview.image = image; } }]; [task resume];
通过代理方法来管理session和task。( 可以获得全部过程,但是较为复杂)
1.
NSURLSessionDelegate用来处理Session层次的事件
2.
NSURLSessionTaskDelegate是使用代理的时候,任何种类task都要实现的代理
3.
NSURLSessionDataDelegate特别用来处理dataTask的事件
代码示例:
#import "ViewController.h" @interface ViewController ()<NSURLSessionDelegate,NSURLSessionTaskDelegate,NSURLSessionDataDelegate> @property (strong,nonatomic)UIImageView * imageview; @property (strong,nonatomic)NSURLSession * session; @property (strong,nonatomic)NSURLSessionDataTask * dataTask; @property (weak, nonatomic) IBOutlet UIProgressView *progressview; @property (nonatomic)NSUInteger expectlength; @property (strong,nonatomic) NSMutableData * buffer; @end static NSString * imageURL = @"http://f12.topit.me/o129/10129120625790e866.jpg"; @implementation ViewController//属性全部采用惰性初始化 #pragma mark - lazy property -(UIImageView *)imageview{ if (!_imageview) { _imageview = [[UIImageView alloc] initWithFrame:CGRectMake(40,40,300,200)]; _imageview.backgroundColor = [UIColor lightGrayColor]; _imageview.contentMode = UIViewContentModeScaleToFill; } return _imageview;} -(NSMutableData *)buffer{ if (!_buffer) { _buffer = [[NSMutableData alloc] init]; } return _buffer;} -(NSURLSession*)session{ if (!_session) { NSURLSessionConfiguration * configuration = [NSURLSessionConfiguration ephemeralSessionConfiguration]; _session = [NSURLSession sessionWithConfiguration:configuration delegate:self delegateQueue:[NSOperationQueue mainQueue]]; } return _session;} -(NSURLSessionDataTask *)dataTask{ if (!_dataTask) { _dataTask = [self.session dataTaskWithURL:[NSURL URLWithString:imageURL]]; } return _dataTask;} #pragma mark - life circle of viewcontroller - (void)viewDidLoad { [self.view addSubview:self.imageview]; [self.dataTask resume];//Task要resume彩绘进行实际的数据传输 [self.session finishTasksAndInvalidate];//完成task就invalidate } #pragma mark - target-action//注意判断当前Task的状态 - (IBAction)pause:(UIButton *)sender { if (self.dataTask.state == NSURLSessionTaskStateRunning) { [self.dataTask pause]; } } - (IBAction)cancel:(id)sender { if (self.dataTask.state == NSURLSessionTaskStateRunning||self.dataTask.state ==NSURLSessionTaskStateSuspended) { [self.dataTask cancel]; } } - (IBAction)resume:(id)sender { if (self.dataTask.state == NSURLSessionTaskStateSuspended) { [self.dataTask resume]; }} -(void)URLSession:(NSURLSession *)session dataTask:(NSURLSessionDataTask *)dataTask didReceiveResponse:(NSURLResponse *)response completionHandler:(void (^)(NSURLSessionResponseDisposition))completionHandler{ NSUInteger length = [response expectedContentLength]; if (length != -1) { self.expectlength = [response expectedContentLength];//存储一共要传输的数据长度 completionHandler(NSURLSessionResponseAllow);//继续数据传输 }else{ completionHandler(NSURLSessionResponseCancel);//如果Response里不包括数据长度的信息,就取消数据传输 UIAlertView * alert = [[UIAlertView alloc] initWithTitle:@"error" message:@"Do not contain property of expectedlength" delegate:nil cancelButtonTitle:@"OK" otherButtonTitles:nil]; [alert show]; }} -(void)URLSession:(NSURLSession *)session dataTask:(NSURLSessionDataTask *)dataTask didReceiveData:(NSData *)data{ [self.buffer appendData:data];//数据放到缓冲区里 self.progressview.progress = [self.buffer length]/((float) self.expectlength);//更改progressview的progress} -(void)URLSession:(NSURLSession *)session task:(NSURLSessionTask *)task didCompleteWithError:(NSError *)error{ if (!error) { dispatch_async(dispatch_get_main_queue(), ^{//用GCD的方式,保证在主线程上更新UI UIImage * image = [UIImage imageWithData:self.buffer]; self.imageview.image = image; self.progressview.hidden = YES; self.session = nil; self.dataTask = nil; }); }else{ NSDictionary * userinfo = [error userInfo]; NSString * failurl = [userinfo objectForKey:NSURLErrorFailingURLStringErrorKey]; NSString * localDescription = [userinfo objectForKey:NSLocalizedDescriptionKey]; if ([failurl isEqualToString:imageURL] && [localDescription isEqualToString:@"cancelled"]) { //如果是task被取消了,就弹出提示框 UIAlertView * alert = [[UIAlertView alloc] initWithTitle:@"Message" message:@"The task is canceled" delegate:nil cancelButtonTitle:@"OK" otherButtonTitles:nil]; [alert show]; }else{ UIAlertView * alert = [[UIAlertView alloc] initWithTitle:@"Unknown type error"//其他错误,则弹出错误描述 message:error.localizedDescription delegate:nil cancelButtonTitle:@"OK" otherButtonTitles:nil]; [alert show]; } self.progressview.hidden = YES; self.session = nil; self.dataTask = nil; }} @end
相关文章推荐
- TCP协议中的三次握手和四次挥手(图解)
- AFNetWorking 中使用HTTPS
- http://bbs.csdn.net/topics/390176122
- https跳转到http session丢失问题
- gre网络细节
- Linux网络编程---ICMP洪水攻击
- window.XMLHttpRequest对象详解
- Android系列之网络(一)----使用HttpClient发送HTTP请求(通过get方法获取数据)
- TCP/IP网络编程 基于Linux编程_3 --优于select的epoll
- TCP/IP网络编程 基于Linux编程_3 --优于select的epoll
- Linux 内核Tcp Socket参数调优
- iOS网络开发之NSURLSession学习<1>
- 跨集群 distcp命令
- VMware NAT Ubuntu 14.04 联网
- Ubuntu 系统用网线连上路由器上网配置
- Linux(Centos6.5)下安装svn服务器,并通过http访问
- Linux 常见网络参数整理
- 问题解决:部分海康网络摄像头无法实现视频流解码与实时预览
- HTTP协议中GET和POST
- HTTP访问控制(CORS)