我已成功在后台下载文件。 应用程序关闭和应用程序重新打开后,仍会按预期下载数据。
但是,为了根据data-download-state显示UI,我需要引用实际的后台任务。我特别想知道是否还有后台任务在运行 - 如果是的话,我需要引用这个特定的任务。
我该怎么做?
根据我的阅读,这个引用应该由downloadSession自动提供,该sessionSession首先被配置为后台会话(即self.downloadService.downloadsSession = self.downloadsSession
)。但这不是以某种方式做到的......
此外,我通过以下方式杀死我的应用程序:a)按下模拟器中的停止按钮或b)双击Home并从多线程视图中滑动App - >这是否有效保持后续任务活动为下一个App-start? (至少didWriteData
方法会同时关闭两个闭包a)或b) - 所以我认为这是好的)
这是我的代码(来自更大的项目 - 但你应该明白这一点)......
let downloadService = SomeDownloadService()
lazy var downloadsSession: URLSession = {
let configuration = URLSessionConfiguration.background(withIdentifier: "SomeID.BGSessionConfiguration")
return URLSession(configuration: configuration, delegate: self, delegateQueue: nil)
}()
override func viewDidLoad() {
super.viewDidLoad()
self.downloadService.downloadsSession = self.downloadsSession
// ...file is created somewhere else...
self.downloadService.startDownload(file)
// *** Until here everything OK - file starts downloading in the background *******
// *** HOW DO I GET A REFERENCE TO THE BACKGROUND TASK RUNNING ???????
// ????
// *** KEEPS PRINTING 0 *** WHY ?????????????????????????
print(self.downloadService.activeDownloads.count
}
// Updates progress info
// *** WORKS WELL - upon second App-Start there is still data coming in *******
func urlSession(_ session: URLSession, downloadTask: URLSessionDownloadTask,
didWriteData bytesWritten: Int64, totalBytesWritten: Int64,
totalBytesExpectedToWrite: Int64) {
guard let url = downloadTask.originalRequest?.url,
let download = self.downloadService.activeDownloads[url] else {
return
}
download.progress = Float(totalBytesWritten) / Float(totalBytesExpectedToWrite)
let totalSize = ByteCountFormatter.string(fromByteCount: totalBytesExpectedToWrite, countStyle: .file)
}
答案 0 :(得分:1)
当您使用downloadTask(with:)
创建任务时,您返回了URLSessionDownloadTask
。只要您的程序仍在运行,您就可以使用该任务来访问下载信息。我相信你的问题是当你的程序被终止并重新启动时如何处理这个问题。
每项任务都有taskIdentifier
。您可以创建一个字典映射标识符,以用于对内部跟踪(URL,常量等)有用的任何内容。重新启动时,您可以调用URLSession.shared.getTasksWithCompletionHandler()
来检索所有正在进行的任务,并使用标识符映射回您用于跟踪它们的任何内容。
如果你唯一关心的是URL,你可以跳过整个标识符步骤,只需使用originalRequest
找出你关心的那个。