gpt4 book ai didi

ios - 如何在 iOS 后台从 Alamofire 获得稳定的连接

转载 作者:行者123 更新时间:2023-11-28 13:24:53 25 4
gpt4 key购买 nike

我从我的 watch 向我的 iOS 应用程序发送命令。目前尚不清楚原因,但如果应用程序在后台运行,我会看到一些错误:

Error Domain=NSURLErrorDomain Code=-997 “失去与后台传输服务的连接”

无法结束 BackgroundTask:不存在标识符为 383 (0x17f) 的后台任务,或者它可能已经结束。中断 UIApplicationEndBackgroundTaskError() 进行调试。

我已经尝试将我的配置更改为后台,为我的配置设置正确的标识符。我的 SessionManager 的静态或惰性实现。对进程进行 deinit 计数。

网络 session 管理器

static var sessionManager: SessionManager = {
let configuration = URLSessionConfiguration.background(withIdentifier: UUID().uuidString + ".WatchOS_Background")
configuration.httpShouldSetCookies = false
configuration.httpMaximumConnectionsPerHost = 4
configuration.timeoutIntervalForRequest = 50
configuration.networkServiceType = .background
configuration.isDiscretionary = false
configuration.shouldUseExtendedBackgroundIdleMode = true
if #available(iOS 13.0, *) {
configuration.allowsExpensiveNetworkAccess = true
configuration.allowsConstrainedNetworkAccess = true
}

let sessionManager = Alamofire.SessionManager(configuration: configuration)
sessionManager.delegate.sessionDidBecomeInvalidWithError = { _, error in
if let error = error {
print(error)
}
}
sessionManager.delegate.taskDidComplete = { _, task, error in
if let error = error {
print(error)
}
}
return sessionManager
}()

请求示例

func getListFromServer(completion: @escaping (ServiceResponse<[Model1]>) -> Void) {
let header: HTTPHeaders = ["User-Agent": UserAgentHelper.fullUserAgentString]
request("/api/1/XXXX", method: .get, parameters: nil, encoding: nil, headers: header).responseData { [weak self] response in
guard let strongSelf = self else { return }
completion(strongSelf.completionResponse(response))
}
}

请求方式

@discardableResult private func request(
_ path: String,
method: HTTPMethod,
parameters: Parameters? = nil,
encoding: ParameterEncoding? = nil,
headers: HTTPHeaders? = nil)
-> DataRequest {
let userEncoding = encoding ?? self.defaultEncoding
let task = beginBackgroundTask()
let dataRequest = NetworkService.sessionManager.request("\(API)\(path)",
method: method,
parameters: parameters,
encoding: userEncoding,
headers: headers)

dataRequest.validate()

self.endBackgroundTask(taskID: task)
return dataRequest
}

开始和结束后台任务

func beginBackgroundTask() -> UIBackgroundTaskIdentifier {
return UIApplication.shared.beginBackgroundTask(withName: "Background_API", expirationHandler: {})
}

func endBackgroundTask(taskID: UIBackgroundTaskIdentifier) {
UIApplication.shared.endBackgroundTask(taskID)
}

我希望从您那里得到一个正确的实现和一个稳定的请求生命周期。

非常感谢您的帮助,对于缺少技术术语,我们深表歉意。

最佳答案

您的核心问题是您没有正确处理后台任务的到期。您必须明确结束任务在其过期处理程序中:

let task = UIApplication.shared.beginBackgroundTask(withName: "Background_API") {
UIApplication.shared.endBackgroundTask(task)
}

我建议你阅读更多 here ,其中 Apple DTS 工程师广泛概述了后台任务处理的要求和边缘情况。

此外,Alamofire 并不真正支持后台 session 。使用带有后台任务处理的前台 session 可能是您最好的选择。一旦 Alamofire SessionManager 被取消初始化,它启动的任何请求都将被取消,即使是后台 session 也是如此。

最后,在 Alamofire 响应处理程序中调用 validate() 是无效的。您应该在添加响应处理程序之前根据请求调用它,因为它会在调用处理程序之前验证响应。如果您之后调用它,它将无法将它产生的错误传递给您的响应处理程序。

关于ios - 如何在 iOS 后台从 Alamofire 获得稳定的连接,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/58558695/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com