2

我正在开发一个应用程序,我需要每天更新我的应用程序中的数据。我决定使用后台获取。我正在从 API 下载数据,所以我使用的是 URLSession。由于不允许完成处理程序,因此performFetchWithCompletionHandler我为此目的使用委托。但我的问题是,当我的应用程序未运行时尝试更新数据时,didRecieve data不会调用该函数。我是在做错什么,还是应该每天使用其他东西从 API 更新我的数据?

我的代码如下:

func createTask(url: String, id: String){
    let accessKey = UserDataService().getCurrentUser().accessToken

    let backgroundConfigObject = URLSessionConfiguration.background(withIdentifier: id + UUID().uuidString)
    let backgroundSession = URLSession(configuration: backgroundConfigObject, delegate: self, delegateQueue: nil)


    var request = URLRequest(url: URL(string: url)!)
    request.setValue("Bearer \(accessKey!)", forHTTPHeaderField: "Authorization")
    request.addValue("application/json", forHTTPHeaderField: "Content-Type")
    request.httpMethod = "GET"

    let task = backgroundSession.dataTask(with: request)

    task.resume()

    print("task resumed")
}

该函数在内部被调用performFetchWithCompletionHandler并创建新的dataTaskdidRecieve data未被调用。

我也尝试在里面添加这段代码performFetchWithCompletionHandler

print("BG FETCH")

let url = "secret url"

var request = URLRequest(url: URL(string: url)!)
request.setValue("SOME KEY", forHTTPHeaderField: "Authorization")
request.addValue("application/json", forHTTPHeaderField: "Content-Type")
request.httpMethod = "GET"

URLSession.shared.dataTask(with: request, completionHandler: { (data, response, error) in
    print("DATA",data)
    completionHandler(.newData)
}).resume()

感谢您的任何建议!

4

1 回答 1

2

我记得在后台只支持上传下载,而不是数据任务。

您是对的,您不能使用带有完成处理程序的调用。你必须提供一个代表。

在 Xcode 中搜索字符串“在后台下载内容”。有相当广泛的文档。

它的要点是系统将在需要时重新启动您的应用程序并调用其application:handleEventsForBackgroundURLSession:completionHandler:方法。

您必须在 info.plist 文件中设置适当的应用权限。(我不记得您是否必须询问用户是否允许进行后台下载。请参阅文档。)

以下是 Apple Xcode 文档的第一部分信息:

在后台下载内容

下载文件时,应用程序应使用 NSURLSession 对象开始下载,以便系统可以在应用程序暂停或终止时控制下载过程。当您为后台传输配置 NSURLSession 对象时,系统会在单独的进程中管理这些传输,并以通常的方式将状态报告回您的应用程序。如果您的应用在传输过程中终止,系统会在后台继续传输,并在传输完成或一项或多项任务需要您的应用注意时启动您的应用(视情况而定)。

要支持后台传输,您必须适当地配置您的 NSURLSession 对象。要配置会话,您必须首先创建一个 NSURLSessionConfiguration 对象并将几个属性设置为适当的值。然后在创建会话时将该配置对象传递给 NSURLSession 的适当初始化方法。

创建支持后台下载的配置对象的流程如下:

使用 NSURLSessionConfiguration 的 backgroundSessionConfigurationWithIdentifier: 方法创建配置对象。将配置对象的 sessionSendsLaunchEvents 属性的值设置为 YES。如果您的应用程序在前台启动传输,建议您还将配置对象的自由裁量属性设置为 YES。根据需要配置配置对象的任何其他属性。使用配置对象来创建你的 NSURLSession 对象。配置完成后,您的 NSURLSession 对象会在适当的时间将上传和下载任务无缝移交给系统。如果任务在您的应用程序仍在运行时完成(无论是在前台还是在后台),会话对象会以通常的方式通知其委托。如果任务尚未完成且系统终止您的应用程序,系统会自动继续在后台管理任务。如果用户终止您的应用程序,系统将取消所有待处理的任务。

当与后台会话关联的所有任务都完成后,系统会重新启动终止的应用程序(假设 sessionSendsLaunchEvents 属性设置为 YES 并且用户没有强制退出应用程序)并调用应用程序委托的 application:handleEventsForBackgroundURLSession:completionHandler : 方法。(系统也可能会重新启动应用程序以处理需要您的应用程序注意的身份验证挑战或其他与任务相关的事件。)在您实现该委托方法时,使用提供的标识符创建一个新的 NSURLSessionConfiguration 和 NSURLSession 对象,其配置与前。系统将您的新会话对象重新连接到之前的任务,并将它们的状态报告给会话对象的代理。

于 2017-08-11T17:06:26.640 回答