IOS AFNetWorking 下載文件 斷點續傳

最近在做視頻音樂方面的東西,整理一下下載文件相關內容

功能需求:
             下載文件,可以顯示進度,暫停,繼續,斷點續傳

1、首先下載文件相關代碼:有三個回調方法:下載進度,下載成功,下載失敗
         要說明的是下載進度顯示:在一個tableview中顯示正在下載的文件,分爲:1)存儲下載文件信息(名字,圖片鏈接,下載地址,文件格式,文件大小等)。2)實時更新進度條,我個人是創建了一個單例,存儲下載地址和下載進度,key值爲地址 ,value爲進度;然後把多個鍵值對存到單例的數組中,然後在下載中心取出來,對cell單獨進行更新

    NSFileManager *fileManager = [NSFileManager defaultManager];
    //檢查本地文件是否已存在
    NSString *fileName = [NSString stringWithFormat:@"%@/%@.mp4", aSavePath, aFileName];

    //檢查附件是否存在
    if ([fileManager fileExistsAtPath:fileName]) {
        NSData *audioData = [NSData dataWithContentsOfFile:fileName];
        [self showHoderTopView:@"已經加入您的緩存"];
        // [self requestFinished:[NSDictionary dictionaryWithObject:audioData forKey:@"res"] tag:aTag];
    }else{
        //創建附件存儲目錄
        if (![fileManager fileExistsAtPath:aSavePath]) {
            [fileManager createDirectoryAtPath:aSavePath withIntermediateDirectories:YES attributes:nil error:nil];
        }
        
        //下載附件
        NSURL *url = [[NSURL alloc] initWithString:aUrl];
        NSURLRequest *request = [NSURLRequest requestWithURL:url];
        
        AFHTTPRequestOperation *operation = [[AFHTTPRequestOperation alloc] initWithRequest:request];

        operation.inputStream   = [NSInputStream inputStreamWithURL:url];
        operation.outputStream  = [NSOutputStream outputStreamToFileAtPath:fileName append:NO];
    
        //下載進度控制
        [operation setDownloadProgressBlock:^(NSUInteger bytesRead, long long totalBytesRead, long long totalBytesExpectedToRead) {
            
            NSString *progress = [NSString stringWithFormat:@"%f",(float)totalBytesRead/totalBytesExpectedToRead];
            
        }];
        
        
        //已完成下載
        [operation setCompletionBlockWithSuccess:^(AFHTTPRequestOperation *operation, id responseObject) {
            [self showHoderTopView:@"緩存成功"];
            
            NSData *audioData = [NSData dataWithContentsOfFile:fileName];
            NSString *byte = [NSString stringWithFormat:@"%d",audioData.length];

            //設置下載數據到res字典對象中並用代理返回下載數據NSData
            // [self requestFinished:[NSDictionary dictionaryWithObject:audioData forKey:@"res"] tag:aTag];
        } failure:^(AFHTTPRequestOperation *operation, NSError *error) {
            
            //下載失敗
            //[self requestFailed:aTag];
        }];
        [operation start];

2、暫停和繼續和取消

       AFHTTPRequestOperation對象方法分別對應 pause  resume  cancel 。問題在於怎麼獲取到這個對象,我用的方法比較粗糙,就是存儲了這個對象到剛纔的單例中,關鍵字也是下載鏈接,只要這個對象存活就能拿到並進行操作。如果對象不存在又要繼續剛纔的任務,接下來就是斷點續傳了


3、斷點續傳

找了很多有關斷點續傳的資料,這篇博客的簡單實用

來自CSDN博客:AFNetworking實現程序重新啓動時的斷點續傳 http://blog.csdn.net/zhaoxy2850/article/details/21383515

//獲取已下載的文件大小
- (unsigned long long)fileSizeForPath:(NSString *)path {
    signed long long fileSize = 0;
    NSFileManager *fileManager = [NSFileManager new]; // default is not thread safe
    if ([fileManager fileExistsAtPath:path]) {
        NSError *error = nil;
        NSDictionary *fileDict = [fileManager attributesOfItemAtPath:path error:&error];
        if (!error && fileDict) {
            fileSize = [fileDict fileSize];
        }
    }
    return fileSize;
}
//開始下載
- (void)startDownload {
    NSString *downloadUrl = @"http://www.xxx.com/xxx.zip";
    NSString *cacheDirectory = [NSSearchPathForDirectoriesInDomains(NSCachesDirectory, NSUserDomainMask, YES) objectAtIndex:0];
    NSString *downloadPath = [cacheDirectory stringByAppendingPathComponent:@"xxx.zip"];
    NSURLRequest *request = [NSURLRequest requestWithURL:[NSURL URLWithString:downloadUrl]];
    //檢查文件是否已經下載了一部分
    unsigned long long downloadedBytes = 0;
    if ([[NSFileManager defaultManager] fileExistsAtPath:downloadPath]) {
	//獲取已下載的文件長度
        downloadedBytes = [self fileSizeForPath:downloadPath];
        if (downloadedBytes > 0) {
            NSMutableURLRequest *mutableURLRequest = [request mutableCopy];
            NSString *requestRange = [NSString stringWithFormat:@"bytes=%llu-", downloadedBytes];
            [mutableURLRequest setValue:requestRange forHTTPHeaderField:@"Range"];
            request = mutableURLRequest;
        }
    }
    //不使用緩存,避免斷點續傳出現問題
    [[NSURLCache sharedURLCache] removeCachedResponseForRequest:request];
    //下載請求
    AFHTTPRequestOperation *operation = [[AFHTTPRequestOperation alloc] initWithRequest:request];
    //下載路徑
    operation.outputStream = [NSOutputStream outputStreamToFileAtPath:downloadPath append:YES];
    //下載進度回調
    [operation setDownloadProgressBlock:^(NSUInteger bytesRead, long long totalBytesRead, long long totalBytesExpectedToRead) {
        //下載進度
        float progress = ((float)totalBytesRead + downloadedBytes) / (totalBytesExpectedToRead + downloadedBytes);
    }];
    //成功和失敗回調
    [operation setCompletionBlockWithSuccess:^(AFHTTPRequestOperation *operation, id responseObject) {
            
    } failure:^(AFHTTPRequestOperation *operation, NSError *error) {
            
    }];
    [operation start];
}

       
發佈了61 篇原創文章 · 獲贊 2 · 訪問量 13萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章