NSURLSessionDownloadTask 在挂起时继续下载

Posted

技术标签:

【中文标题】NSURLSessionDownloadTask 在挂起时继续下载【英文标题】:NSURLSessionDownloadTask continues download while suspended 【发布时间】:2017-05-16 12:48:19 【问题描述】:

我正在使用 NSURLSessionDownloadTask 下载文件。在应用程序中的某一时刻,有必要暂停下载一小段时间,然后再继续下载。我尝试使用暂停方法暂停下载,但任务继续下载。 NSURLSessionTask 的方法挂起状态的 Apple 文档:

任务在暂停时不会产生网络流量并且不会超时。下载任务可以在以后继续传输数据。所有其他任务在恢复后必须重新开始。

这似乎表明我的做法是对的,但结果却不如预期。我能够在 Playground 中使用以下代码重现它。

import UIKit

let backgroundSessionConfiguration = URLSessionConfiguration.background(withIdentifier: "some-identifier")
let backgroundSession = Foundation.URLSession(configuration: backgroundSessionConfiguration, delegate: nil, delegateQueue: nil)

let request = URLRequest(url: URL(string: "http://google.com")!)
let task = backgroundSession.downloadTask(with: request)

task.state.rawValue

task.resume()
task.state.rawValue

task.suspend()
task.state.rawValue

sleep(10)

task.state.rawValue

任务状态的预期结果将是 1, 0, 1, 1(0 - 下载,1 - 暂停,2 - 取消,3 - 完成)。实际结果是 1, 0, 1, 3。这意味着尽管任务已暂停,但它仍会继续下载并在下载完成后将其标记为已完成。

应用程序中的设置更复杂,任务状态不能总是被复制(在 Playground 中结果似乎总是相同)但暂停任务后的结果总是成功下载文件(包括进度回调被调用)。

问题: 难道我做错了什么?我是否误解了 Apple 文档,无法以这种方式暂停下载任务?

当我在应用程序中遇到这个问题时,我的第一个直觉是我在其他地方调用 resume 导致下载继续,但在调试代码后似乎并非如此 + Playground 调查结果支持这一点好。

【问题讨论】:

【参考方案1】:

可能不是您正在寻找的答案,但 Apple 开发关系代表 confirmed in their dev forums 表示,在某些情况下,使用 suspend 可能不会真正暂停后台下载:

[...] 挂起的任务仍然可以在线上活动; suspend 所做的只是阻止它在内部取得进展、发出回调等等。

他们继续建议改用cancel(byProducingResumeData:)

如果您要实现长期暂停(例如,用户想要暂停下载),您最好致电-cancelByProducingResumeData:

【讨论】:

谢谢,很高兴知道!我遇到这个问题已经一年了,所以我不记得我们是如何解决它的。可能重写了一些其他代码来规避它。不过下次可能会有用。

以上是关于NSURLSessionDownloadTask 在挂起时继续下载的主要内容,如果未能解决你的问题,请参考以下文章

NSURLSessionDownloadTask 进度回调不顺畅?

在 NSMutableDictionary 中设置 NSURLSessionDownloadTask

NSUrlSessionDownloadTask - 进入后台时出现didCompleteWithError

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

NSURLSessionDownloadTask 在挂起时继续下载

在下载字节时从 NSURLSessionDownloadTask 访问字节