对于我的许多端点,我要求在请求中传递一个承载令牌,以对用户进行身份验证。因此,如果过期,我还需要刷新用户的令牌。
我发现this question是我的起点,但是我仍然不确定某些事情以及如何实现它们。
正如上述问题的答案所暗示的,我为MoyaProvider
创建了一个扩展名:
extension MoyaProvider {
convenience init(handleRefreshToken: Bool) {
if handleRefreshToken {
self.init(requestClosure: MoyaProvider.endpointResolver())
} else {
self.init()
}
}
static func endpointResolver() -> MoyaProvider<Target>.RequestClosure {
return { (endpoint,closure) in
//Getting the original request
let request = try! endpoint.urlRequest()
//assume you have saved the existing token somewhere
if (#tokenIsnotExpired#) {
// Token is valid,so just resume the original request
closure(.success(request))
return
}
//Do a request to refresh the authtoken based on refreshToken
authenticationProvider.request(.refreshToken(params)) { result in
switch result {
case .success(let response):
let token = response.mapJSON()["token"]
let newRefreshToken = response.mapJSON()["refreshToken"]
//overwrite your old token with the new token
//overwrite your old refreshToken with the new refresh token
closure(.success(request)) // This line will "resume" the actual request,and then you can use accessTokenPlugin to set the Authentication header
case .failure(let error):
closure(.failure(error)) //something went terrible wrong! Request will not be performed
}
}
}
}
我还为TargetType
创建了一个扩展名,如下所示:
import Moya
public protocol TargetTypeExtension: TargetType,accessTokenAuthorizable {}
public extension TargetTypeExtension {
var baseURL: URL { return URL(string: Constants.apiUrl)! }
var headers: [String: String]? { return nil }
var method: Moya.Method { return .get }
var authorizationType: AuthorizationType { return .bearer }
var sampleData: Data { return Data() }
}
这是它的一种实现方式:
import Moya
public enum Posts {
case likePost(postId: Int)
case getcomments(postId: Int)
}
extension Posts: TargetTypeExtension {
public var path: String {
switch self {
case .likePost(_): return "posts/like"
case .getcomments(_): return "posts/comments"
}
}
public var authorizationType: AuthorizationType {
switch self {
case .likePost(_): return .bearer
case .getcomments(_): return .none
}
}
public var method: Moya.Method {
switch self {
case .likePost,.getcomments:
return .post
}
}
public var task: Task {
switch self {
case let .likePost(postId):
return .requestParameters(parameters: ["postId": postId],encoding: JSONEncoding.default)
case let .getcomments(postId):
return .requestParameters(parameters: ["postId": postId],encoding: JSONEncoding.default)
}
}
}
如您所见,我的likePost
请求不需要承载令牌,而我的getcomments
请求则不需要承载令牌。
所以我有几个问题:
- 我将如何修改我的
MoyaProvider
扩展名以使用Moya的accessTokenPlugin
,found here? - 如果针对特定请求的
MoyaProvider
是AuthorizationType
,我将如何修改我的.none
扩展名以使其不需要承载令牌?
谢谢!