iOS开发之网络编程--2、NSURLSessionDownloadTask文件下载

本文内容大纲:

1、回顾NSURLSessionTask

2、NSURLSessionDownloadTask大文件之block下载

3、NSURLSessionDownloadTask大文件之代理方法下载

4、NSURLSessionDownloadTask大文件之代理方法实现断点续传下载

前言:如果读者是第一次阅读或者是学习关于本篇要介绍的NSURLSession的知识,最好先阅读本人前篇《iOS开发之网络编程--1、NSURLSession的基本使用》然后再学习本篇比较好。

1、回顾NSURLSessionTask:

使用NSURLSession就需要用到NSURLSessionTask,所以关于Task的类和其子类的关系还是要了解的:

    

本篇讲解的是大文件下载,既然是"下载",所以自然要用到的是NSURLSessionDownloadTask。

2、NSURLSessionDownloadTask大文件之block下载

测试的API接口:http://120.25.226.186:32812/resources/images/minion_08.png (因为Block的缺点,所以这里用并不打的图片文件作为测试)

  2-1、类、方法、属性介绍:

    NSURLSession

      +(NSURLSession*)sharedSession;                        单例,直接创建会话session对象

      - (NSURLsessionDownloadTask*)downloadTaskWithURL:completionHandler:; 根据URL来创建会话的下载任务downloadTask,完成的话回调block

    NSURLsessionDownloadTas

      - (void)resume;                                启动并执行任务

  2-2、源码展示:

  2-3、缺点:

      Block下载方式不适合大文件下载,因为该方法需要等到文件下载完毕了,才会回调completionHandler后面的block参数,然后才可以在这个block参数可以

    获取location(文件下载缓存的路径)、response(响应)、error(错误信息)。

      这样的话,对于大文件,我们就无法实时的在下载过程中获取文件的下载进度了。

3、NSURLSessionDownloadTask大文件之代理方法下载

测试的API接口:http://120.25.226.186:32812/resources/videos/minion_02.mp4  (这回用的是大文件哦,但也不会太大,本篇基础练习用,不会让你下载都要花个好几十分钟以上的时间??)

  3-1、类、方法、属性:

    NSURLSession

      +(NSURLSession*)sessionWithConfiguration:delegate:delegateQueue:;     根据会话配置对象并设置代理和代理的执行队列来创建会话NSURLSession对象

      - (NSURLSessionDownloadTask*)downloadTaskWithURL;           根据URL直接创建会话的任务

    NSURLSessionConfiguration

      +(NSURLSessionConfiguration*)defaultSessionConfiguration;         创建默认的会话配置对象

    NSURLSessionDownloadTask

      - (void)resume                                 执行会话任务

       协议和代理方法:

    <NSURLSessionDownloadDelegate> 

    -(void)URLSession:(NSURLSession *)session downloadTask:(NSURLSessionDownloadTask *)downloadTask
          didWriteData:(int64_t)bytesWritten totalBytesWritten:(int64_t)totalBytesWritten totalBytesExpectedToWrite:(int64_t)totalBytesExpectedToWrite

       session当前会话  downloadTask当前会话任务  bytesWritten本次写入数据大小  totalBytesWritten已经写入数据大小  totalBytesExpectedToWrite要下载的文件总大小

    -(void)URLSession:(NSURLSession *)session downloadTask:(NSURLSessionDownloadTask *)downloadTask
               didResumeAtOffset:(int64_t)fileOffset expectedTotalBytes:(int64_t)expectedTotalBytes

       didResumeAtOffset恢复下载时调用的代理方法

    -(void)URLSession:(NSURLSession *)session downloadTask:(NSURLSessionDownloadTask *)downloadTask
                             didFinishDownloadingToURL:(NSURL *)location

       didFinishDownloadingToURL:(NSURL *)location  内部已经实现了边下载边写入数据到沙盒的操作

       downloadTask                    内部时可以拿到响应头信息

    -(void)URLSession:(NSURLSession *)session task:(NSURLSessionTask *)task didCompleteWithError:(NSError *)error

       请求失败返回错误信息调用的代理方法

   3-2、源码展示

    

   3-3、相比block下载方式的优点:

        可以实时获取下载进度。

   3-4、源码下载:

      百度云分享链接: http://pan.baidu.com/s/1i4jmNIl 密码: m5jk

   3-5、可以看到的效果:

      

      然后这个路径下你可以找到下载的mp4文件。

4、NSURLSessionDownloadTask大文件之代理方法实现断点续传下载

  接下来的示例是在3、NSURLSessionDownloadTask大文件之代理方法下载的基础上进一步叙述的。

  使用测试的API接口仍然是那个:http://120.25.226.186:32812/resources/videos/minion_02.mp4

   4-1、为了更好的实现断点续传,这里需要添加三个按钮实现:开始下载、暂停下载、恢复下载,并关联到代码中。

     

   4-2、断点续传涉及到的类和方法

    NSURLSessionDownloadTask:

        - (void) suspend; 暂停 ,可以恢复

        - (void) cancel; 取消,不可以恢复

        - (void) cancelByProducingResumeData:^(NSData * _Nullable resumeData) : ; 取消的

        - (void) resume; 在创建新的任务下resume,相当于重新启动任务

   4-3、使用上面的方法注意

    4-3-1、如果使用suspend方法暂停下载,因为是可恢复的,那么对应的下载任务对象是唯一的。

        

    使用的时候suspend要和resume成对使用,都是同一个NSURLSessionDownloadTask调用的对象方法。

    4-3-2、如果使用cancel,就相当于同时NSURLSessionDwonloadTask任务也被取消了。所以如果要重新下载就需要重新创建NSURLSessionDownloadTask对象

        与此同时,就不能再重头开始下载了,应该是要重之前已经下载的部分末尾开始下载。

      下面先改改UIButton的显示字符串为"取消"

      

      如果使用cancel是无法恢复下载,但是为了能够恢复下载就只能用 cancelByProducingResumeData:^(NSData * _Nullable resumeData)方法了。

      其中这个方法中的resumeData存储的是之前已经下载好的数据相关的信息:文件名,存储位置,已经下载好的数据的长度等等信息,并不是下载的数据本身哦。

      恢复下载也是需要通过这个resumeData来恢复,然后继续下载。同时也要重新创建下载任务对象NSURLSessionDownloadTask。

        

       

      这中方法,会有一个bug,那就如果用户再此点击"继续下载"按钮,就创建新的任务,一个新的任务同时会新的线程。

    4-4、源码下载:

      百度云分享链接: http://pan.baidu.com/s/1qXnIsYK 密码: ekx2

    4-5、无法处理的需求:

      对于退出应用程序,然后重启程序,想要断点继续下载无法实现,只能重新下载。

      首先,貌似可行的思路:可以将resumData存储在本地,但是存储的前提是,用户点击了"取消下载"按钮,实际情况中往往是用户直接退出应用程序而一般不会事先去点击一下"取消按钮",

      如果是这样的话,resumeData并没有存储在本地,就无法实现重启应用程序之后再继续下载。

     

转载注明出处:http://www.cnblogs.com/goodboy-heyang/p/5195806.html,尊重劳动成果。

时间: 2024-10-13 17:42:43

iOS开发之网络编程--2、NSURLSessionDownloadTask文件下载的相关文章

iOS开发之网络编程--使用NSURLConnection实现大文件下载

主要思路(实现下载数据分段写入缓存中) 1.使用NSURLConnectionDataDelegate以及代理方法.2.在成功获取响应的代理方法中,获得沙盒全路径,并在该路径下创建空文件和文件句柄.3.在获取data的代理方法中,先设置句柄在沙盒全路径文件末尾,然后通过句柄写入data数据.4.在文件下载完的代理方法中,关闭句柄同时设置句柄引用为nil释放句柄和指针. 使用句柄的思路图(红色的箭头表示句柄,灰色的箭头表示移动的路径): 代码关键词: 类:NSFileHandle的方法 1.fil

IOS开发之网络编程(请求数据和断点续传)

IOS开发中网络编程应用场景:JSON数据获取,网络数据的下载. 一:请求JSON数据一般用异步请求的方式,如果用同步请求,则会造成IOS界面的执行过程阻塞,即界面部分在请求数据的过程中必须等待数据加载完毕. JSON数据的获取步骤: 1.设置网络地址的字符串:NSString *URLString = @"http://www.baidu.com"; 2.创建URL:NSURL *URL = [NSURL URLWithString:URLString]; 3.创建请求:NSURLR

iOS开发之网络编程--使用NSURLConnection实现大文件断点续传下载+使用输出流代替文件句柄

前言:本篇讲解,在前篇iOS开发之网络编程--使用NSURLConnection实现大文件断点续传下载的基础上,使用输出流代替文件句柄实现大文件断点续传.    在实际开发中,输入输出流用的比较少,但是用起来也是很方便的.iOS开发用到的输入输出流和在Java中的输入输出流是几乎一样的,本质也是一个意思:将网络返回的数据当做流来处理.    输入输出的理解:输入到哪里?输出到哪里?这个问题不难理解,输入输出是要站着服务器角度来思考的,下面用图来解释:    代码关键词: 1.在接收到响应头的代理

iOS开发之网络编程--5、NSURLSessionUploadTask+NSURLSessionDataDelegate代理上传

前言:关于NSURLSession的主要内容快到尾声了,这里就讲讲文件上传.关于文件上传当然就要使用NSURLSessionUploadTask,这里直接讲解常用的会和代理NSURLSessionDataDelegate一起搭配实现文件上传功能.另外,下面使用的文件上传思路是和NSURLConnection中本人之前的随笔<iOS开发之网络编程--使用NSURLConnection实现文件上传>提到的上传思路是一样的,都是要将请求信息拼接起来,然后传入到请求里进行上传.这个拼接过程是必要的,但

iOS开发之网络编程--XCode7 更新以来需要手动设置的内容

XCode7 更新以来,默认是不允许加载一些http网络请求,是因为现在网络大部分使用更安全的https协议头. 所以,iOS网络编程如果出现请求无效,事先考虑是否设置一下了以下操作:

iOS开发之网络编程--文件下载(一)

文件下载方式: 如果下载的文件比较小,下载方式: 直接用NSData的 +(id)dataWithContentsOfURL:(NSURL*)url; 利用NSURLConnection发送一个HTTP请求去下载 如果是下载图片,还可以利用SDWebImage框架(本文这里不描述) 如果下载的文件比较大,下载方式: 使用NSConnectionDataDelegate代理方法 建议使用NSURLSession或者第三方框架(本文这里不描述) 代码示例: 先给出用来做代码练习的API接口 小图片:

iOS开发之网络编程--6、NSURLSessionConfiguration笔记

NSURLSessionConfiguration对象用于初始化NSURLSession对象. 展开请求级别中与NSMutableURLRequest相关的可供选择的方案,我们可以看到NSURLSessionConfiguration对于会话如何产生请求,提供了相当多的控制和灵活性.从网络访问性能,到cookie,安全性,缓存策略,自定义协议,启动事件设置,以及用于移动设备优化的几个新属性,你会发现你一直在寻找的,正是NSURLSessionConfiguration. 会话在初始化时复制它们的

iOS开发之网络编程--1、NSURLSession的基本使用

前言:学习NSURLSession的使用之前,先学习一篇关于NSURLSession的好文章<From NSURLConnection to NSURLSession>或者是国内的译文<从 NSURLConnection 到 NSURLSession>,或者不用学习本人的博客园笔记直接学习<从 NSURLConnection 到 NSURLSession>也是可以的,这篇对NSURLSession的使用有着挺详细的论述.但是本文先粗略介绍一下NSURLSession的基

iOS开发之网络编程--获取文件的MIMEType

前言:有时候我们需要获取文件的MIMEType的信息,下面就介绍关于获取MIMEType的方法. 1.直接百度搜索关键字"MIMEType",你会找到,然后查吧: 2.用代码获取文件的MIMEType信息: 1 #import "GetMIMEType.h" 2 3 #import <MobileCoreServices/MobileCoreServices.h> 4 5 @implementation GetMIMEType 6 7 #pragma m