Abd*_*dou 5 swift swiftui combine
我正在尝试在 Swift 5 和适用于 iOS 的组合框架中实施刷新令牌策略。
我不打算使用任何第三方包,只使用框架提供的,`URLSession.dataTaskPublisher`,所以 mu 的目标是:
这是一个非常简单的用例,但似乎很难在 Combine 中实现,这使得它在任何现实生活场景中都很难使用。
欢迎任何帮助!
这是我的尝试,不幸的是不起作用
private func dataTaskPublisherWithAuth(for request: URLRequest) -> URLSession.DataTaskPublisher {
return session.dataTaskPublisher(for: request)
.tryCatch { error -> URLSession.DataTaskPublisher in
guard error.errorCode == 401 else {
throw error
}
var components = URLComponents(url: self.baseUrl, resolvingAgainstBaseURL: true)
components?.path += "/refresh"
components?.queryItems = [
URLQueryItem(name: "refresh_token", value: KeychainHelper.RefreshToken),
]
let url = components?.url
var loginRequest = URLRequest(url: url!)
loginRequest.httpMethod = "GET"
loginRequest.setValue("application/json", forHTTPHeaderField: "Content-Type")
return session.dataTaskPublisher(for: loginRequest)
.decode(type: LoginResponse.self, decoder: JSONDecoder())
.map { result in
if result.accessToken != nil {
// Save access token
KeychainHelper.AccessToken = result.accessToken!
KeychainHelper.RefreshToken = result.refreshToken!
KeychainHelper.ExpDate = Date(timeIntervalSinceNow: TimeInterval(result.expiresIn!))
}
return result
}
.flatMap { data -> URLSession.DataTaskPublisher in
session.dataTaskPublisher(for: request)
}
}.eraseToAnyPublsiher()
}
Run Code Online (Sandbox Code Playgroud)
您应该.tryCatch在此处使用Publisher 上的方法。这使您可以用另一个发布者替换错误(例如用刷新请求替换错误 401,然后是map switchToLastest身份验证请求)或另一个错误(在这种情况下,如果它不是 401,则只抛出原始错误)。
请注意,您可能不应该flatMap在这里使用,因为它与.flatMapLatestRx 或.flatmap(.latest)Reactive Swift 中的不同。您想养成在Combine中使用.mapand的习惯switchToLatest(即apple 决定扁平化和映射是两个独立的操作符)。如果您不这样做,您将在某些生成多个内部发布者的地方遇到麻烦,例如在您键入时搜索,因为您将获得所有这些,而不是获取最新的内部值,因为网络请求在不确定的时间内完成。
| 归档时间: |
|
| 查看次数: |
2141 次 |
| 最近记录: |