美文网首页
NSURLSession

NSURLSession

作者: chaoone | 来源:发表于2017-03-15 00:07 被阅读0次

    简介:

    • 用于替代NSURLConnection
    • 支持后台运行的网络任务
    • 暂停、停止、重启网络任务,不再需要NSOperation封装
    • 请求可以使用同样的配置容器
    • 直接使用系统方法可以实现文件上传和下载
    • 通过代理方法可以获取文件上传和下载的进度
    • block 和代理都对文件上传和下载起作用
    • 当文件上传时,block和代理可以同时使用
    • 当文件下载时,block和代理不要同时使用

    说明

    为了方便程序员使用,苹果提供了一个全局 session.
    所有的 任务(Task) 都是由 session 发起的.
    所有的任务默认是挂起的,需要 resume.
    session可以自定义,自定义的时候可以同时设置代理.


    结构图

    使用NSURLSession发送GET请求

    - (void)sendRequest
    {
        // 1.URL
        NSURL *URL = [NSURL URLWithString:@"http://localhost/demo.json"];
    
        // 2.session
        NSURLSession *session = [NSURLSession sharedSession];
    
        // 3.发起任务(Task)
        // 请求默认是GET的.所以不需要创建request.
        // completionHandler : 服务器把数据返回到客户端之后,会自动调用的
        NSURLSessionDataTask *dataTask = [session dataTaskWithURL:URL completionHandler:^(NSData * _Nullable data, NSURLResponse * _Nullable response, NSError * _Nullable error) {
            // 5.处理响应
            if (error==nil && data!=nil && data.length>0) {
    
                // 反序列化
                id result = [NSJSONSerialization JSONObjectWithData:data options:0 error:NULL];
                NSLog(@"%@",result);
    
            } else {
                NSLog(@"出错 %@",error);
            }
        }];
    
        // 4.启动任务(resume)
        [dataTask resume];
    }
    
    • 如果不想自己创建session,可以直接使用苹果提供的单例session;
      一般在要使用session的代理方法或者需要设置session的Configuration时会自定义session.
    • 任务(task)是不需要新建的,直接由session发起.
      普通的获取数据的任务指定为NSURLSessionDataTask.
    • 任务默认是挂起的,需要手动开启任务.
      NSURLSession的网络请求默认是GET.

    使用NSURLSession发送POST请求

    - (void)loadData
    {
        // 1.URL
        NSURL *URL = [NSURL URLWithString:@"http://localhost/php/login/login.php"];
    
        // 2.request
        NSMutableURLRequest *requestM = [NSMutableURLRequest requestWithURL:URL];
        // 设置请求方法
        requestM.HTTPMethod = @"POST";
        // 设置请求体
        NSString *body = @"username=zhangsan&password=zhang";
        requestM.HTTPBody = [body dataUsingEncoding:NSUTF8StringEncoding];
    
        // 3.session
        NSURLSession *session = [NSURLSession sharedSession];
    
        // 4.发起任务(task)
        NSURLSessionDataTask *dataTask = [session dataTaskWithRequest:requestM completionHandler:^(NSData * _Nullable data, NSURLResponse * _Nullable response, NSError * _Nullable error) {
            // 6.处理响应
            if (error==nil && data!=nil && data.length>0) {
    
                // 反序列化
                id result = [NSJSONSerialization JSONObjectWithData:data options:0 error:NULL];
                NSLog(@"%@",result);
    
            } else {
                NSLog(@"出错 %@",error);
            }
        }];
    
        // 5.启动任务(resume)
        [dataTask resume];
    }
    
    • NSURLSession实现POST请求,需要创建可变请求对象,用于设置请求方法和请求体.
    • POST请求也是属于普通的获取数据的任务.所以任务也是指定为NSURLSessionDataTask.

    NSURLSession文件下载的代理工作队列

    • nil - 异步回调 和 实例化一个 操作队列的效果是一样的!

    • [[NSOperationQueue alloc] init] - 子线程中执行代理方法

    注意:下载本身的线程"只有一条".
    代理回调可以在"多个线程"回调!

    • [NSOperationQueue mainQueue] - 主线程中执行代理方法

    下载本身是异步执行的,这一点和 NSURLConnection 是一样的.
    指定代理执行的队列,不会影响到下载本身的执行.
    NSURLSession 即使在主线程回调也不会造成阻塞.
    如何选择队列

    网络访问结束后,如果不需要做复杂的操作,可以指定主队列,这样不用考虑线程间通讯.

    使用NSURLSessionDownloadDelegate时,回调和代理方法不能同时使用,一旦同时使用,代理方法就不再执行。
    文件下载之后,会默认的被删除,所以文件下载接收后需要自己实现缓存。

    相关文章

      网友评论

          本文标题:NSURLSession

          本文链接:https://www.haomeiwen.com/subject/gcaddttx.html