网络编程05-通过NSURLSessionDownloadTask来下载

这里介绍NSURLSessionDownloadTask的两种下载文件的方式.一种是block形式的,代码精简,但是无法控制下载进度,以及断点下载.
第二种是delegate的形式,功能强大,既可以控制下载进度,又可以设置断点下载.
在项目中 大家可以根据需要选择最佳的实践方案:

1.NSURLSessionDownloadTask的block形式.

- (NSURLSessionDownloadTask *)downloadTaskWithRequest:(NSURLRequest *)request completionHandler:(void (^)(NSURL *location, NSURLResponse *response, NSError *error))completionHandler

downloadTaskWithURL: 该方法默认已经实现了边下载边写入.所以在 completionHandler 这个 block 里,我们需要把文件从一个临时地址移动到一个永久的地址保存起来.通过指定 completionHandler 这个 block 将创建一个隐式的 delegate,来替代该 task 原来的 delegate——session。
参数解释:
第一个参数: 需要下载的文件的路径

第二个参数:

  • location: 下载好的文件在手机磁盘上的位置,临时存储
  • response: 响应头
  • error: 请求是否有错

其他两种block形式分别根据url,还有恢复数据来创建相应的
NSURLSessionDownloadTask.如下所示:

- (NSURLSessionDownloadTask *)downloadTaskWithURL:(NSURL *)url completionHandler:(void (^)(NSURL *location, NSURLResponse *response, NSError *error))completionHandler

- (NSURLSessionDownloadTask *)downloadTaskWithResumeData:(NSData *)resumeData completionHandler:(void (^)(NSURL *location, NSURLResponse *response, NSError *error))completionHandler 

下面是一个下载image的实例,然后把image移动

    // 1.创建NSURLSession
    NSURLSession *session = [NSURLSession sharedSession];
    // 2.创建Task
    NSURL *url = [NSURL URLWithString:@"http://120.25.226.186:32812/resources/images/minion_02.png"];
    NSURLSessionDownloadTask *task = [session downloadTaskWithURL:url completionHandler:^(NSURL *location, NSURLResponse *response, NSError *error) {
        NSString *dir = [NSSearchPathForDirectoriesInDomains(NSCachesDirectory, NSUserDomainMask, YES) lastObject];
        // 1.生成需要移动到得路径
        NSString *toPath = [dir stringByAppendingPathComponent:[response.suggestedFilename lastPathComponent]];
        NSLog(@"%@",toPath);
        // 2.移动文件
        NSFileManager *manager = [NSFileManager defaultManager];
        [manager moveItemAtURL:location toURL:[NSURL fileURLWithPath:toPath] error:nil];
    }];
    // 3.启动任务
    [task resume];

2.使用delegate进行下载


这里写图片描述

#import "ViewController.h"

@interface ViewController ()<NSURLSessionDownloadDelegate>

@property (weak, nonatomic) IBOutlet UIProgressView *progressView;
- (IBAction)startBtnClick:(UIButton *)sender;
- (IBAction)pauseBtnClick:(UIButton *)sender;
- (IBAction)goOnBtnClick:(UIButton *)sender;

/** 任务 */
@property (nonatomic, strong) NSURLSessionDownloadTask *task;

/** session */
@property (nonatomic, strong) NSURLSession *session;

/** 恢复信息 */
@property (nonatomic, strong) NSData *resumeData;
@end

@implementation ViewController

- (IBAction)startBtnClick:(UIButton *)sender {

    // 1.创建NSURLSession
    NSURLSession *session = [NSURLSession sessionWithConfiguration:[NSURLSessionConfiguration defaultSessionConfiguration] delegate:self delegateQueue:[NSOperationQueue mainQueue]];
    self.session = session;

    // 2.创建Task
    NSURL *url = [NSURL URLWithString:@"http://120.25.226.186:32812/resources/videos/minion_02.mp4"];
    self.task = [session downloadTaskWithURL:url];

    // 3.启动任务
    [self.task resume];
}

- (IBAction)pauseBtnClick:(UIButton *)sender
{
    // resumeData : 保存了当前用户下载的信息
    // 只要有了这些信息, 以后就可以通过这些信息恢复下载
    [self.task cancelByProducingResumeData:^(NSData *resumeData) {
        self.resumeData = resumeData;
    }];
}

- (IBAction)goOnBtnClick:(UIButton *)sender
{
    self.task = [self.session downloadTaskWithResumeData:self.resumeData];
    [self.task resume];

}

#pragma mark - NSURLSessionDownloadDelegate
/*
 1.接收到服务器返回的数据
 正在写入数据
 bytesWritten: 当前这一次写入的数据大小
 totalBytesWritten: 已经写入到本地文件的总大小
 totalBytesExpectedToWrite : 被下载文件的总大小
 */

- (void)URLSession:(NSURLSession *)session downloadTask:(NSURLSessionDownloadTask *)downloadTask didWriteData:(int64_t)bytesWritten totalBytesWritten:(int64_t)totalBytesWritten totalBytesExpectedToWrite:(int64_t)totalBytesExpectedToWrite
{
    self.progressView.progress = 1.0 * totalBytesWritten / totalBytesExpectedToWrite;
}

/*
 2.恢复下载时调用
 fileOffset : 恢复之后要从文件的什么地方开始写入数据
 expectedTotalBytes: 文件总共需要下载的大小
 */
- (void)URLSession:(NSURLSession *)session downloadTask:(NSURLSessionDownloadTask *)downloadTask didResumeAtOffset:(int64_t)fileOffset expectedTotalBytes:(int64_t)expectedTotalBytes
{
    NSLog(@"fileOffset = %lld, expectedTotalBytes = %lld", fileOffset, expectedTotalBytes);
}

//3.下载完成
- (void)URLSession:(NSURLSession *)session downloadTask:(NSURLSessionDownloadTask *)downloadTask didFinishDownloadingToURL:(NSURL *)location
{
    // 1.生成需要移动到得路径
    NSString *dir = [NSSearchPathForDirectoriesInDomains(NSCachesDirectory, NSUserDomainMask, YES) lastObject];
    NSString *toPath = [dir stringByAppendingPathComponent:downloadTask.response.suggestedFilename];
    // 2.移动文件
    NSFileManager *manager = [NSFileManager defaultManager];
    [manager moveItemAtURL:location toURL:[NSURL fileURLWithPath:toPath] error:nil];
}

//4.请求完毕,如果有错误, 那么error有值
- (void)URLSession:(NSURLSession *)session task:(NSURLSessionTask *)task didCompleteWithError:(NSError *)error
{
    NSLog(@"didCompleteWithError");
}

@end
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值