Alamofire 的 Swift 扩展方法返回 SwiftyJSON 结果
Posted
技术标签:
【中文标题】Alamofire 的 Swift 扩展方法返回 SwiftyJSON 结果【英文标题】:Swift extension method for Alamofire to return SwiftyJSON result 【发布时间】:2017-01-23 06:11:19 【问题描述】:我将一个应用程序从 Swift 2.2 迁移到 3.0,它使用了来自 GitHub 上的 Alamofire-SwiftyJSON 项目的扩展方法。 Alamofire-SwiftyJSON 允许接收来自 Alamofire 网络请求的响应,转换为 SwiftyJSON 实例,如下所示:
Alamofire.request(.GET, "http://httpbin.org/get", parameters: ["foo": "bar"])
.responseSwiftyJSON( (request, response, json, error) in
print(json) // json is a SwiftyJSON 'JSON' instance
print(error)
)
在撰写此问题时,尚未针对 Swift 3 更新 Alamofire-SwiftyJSON 项目。我正在寻找适用于 Swift 3+ 和 Alamofire 4+ 的 responseSwiftyJSON
扩展方法的等效实现。
【问题讨论】:
【参考方案1】:扩展方法
此解决方案包含来自 SwiftyJSON readme 的关于使用 Alamofire 的建议。
它基于 ResponseSerialization.swift 中的 Alamofire 包含的类似扩展:
DataRequest.responseJSON(queue:options:completionHandler:)
DataRequest.jsonResponseSerializer(options:)
此解决方案适用于 Swift 3 及更高版本。它使用 Alamofire 4.2+ 和 SwiftyJSON 3.1.3+ 进行了测试。
import Alamofire
import SwiftyJSON
extension DataRequest
/// Adds a handler to be called once the request has finished.
///
/// - parameter options: The JSON serialization reading options. Defaults to `.allowFragments`.
/// - parameter completionHandler: A closure to be executed once the request has finished.
///
/// - returns: The request.
@discardableResult
public func responseSwiftyJSON(
queue: DispatchQueue? = nil,
options: JSONSerialization.ReadingOptions = .allowFragments,
completionHandler: @escaping (DataResponse<JSON>) -> Void) -> Self
return response(
queue: queue,
responseSerializer: DataRequest.swiftyJSONResponseSerializer(options: options),
completionHandler: completionHandler
)
/// Creates a response serializer that returns a SwiftyJSON instance result type constructed from the response data using
/// `JSONSerialization` with the specified reading options.
///
/// - parameter options: The JSON serialization reading options. Defaults to `.allowFragments`.
///
/// - returns: A SwiftyJSON response serializer.
public static func swiftyJSONResponseSerializer(
options: JSONSerialization.ReadingOptions = .allowFragments) -> DataResponseSerializer<JSON>
return DataResponseSerializer _, response, data, error in
let result = Request.serializeResponseJSON(options: options, response: response, data: data, error: error)
switch result
case .success(let value):
return .success(JSON(value))
case .failure(let error):
return .failure(error)
使用示例:
Alamofire.request("https://httpbin.org/get").validate().responseSwiftyJSON
response in
print("Response: \(response)")
switch response.result
case .success(let json):
// Use SwiftyJSON instance
print("JSON: \(json)")
case .failure(let error):
// Handle error
print("Error: \(error)")
【讨论】:
粗糙但优雅,一旦你了解 Alamofire 正在做什么。如果 queue 为 nil,则在 queue 正在运行的线程或主线程上调用 completionHandler。在 Alamofire 内部的 NSOperationQueue 上调用 responseSerializer。我会在 SWiftyJSON 自述文件中添加对 validate() 的调用。 感谢@user992167 的反馈!我按照您的建议添加了 validate() 方法。以上是关于Alamofire 的 Swift 扩展方法返回 SwiftyJSON 结果的主要内容,如果未能解决你的问题,请参考以下文章
iOS swift 使用 alamofire 在应用程序和共享扩展程序之间共享 cookie
Alamofire 4、Swift 3:无法返回 StatusCode
Swift 2 - 使用 Alamofire 时函数不返回 Bool