[英]Swift closure with Alamofire
我正在對服務器進行API調用。 我正在利用Alamofire來解決這個問題。 我正在嘗試創建一個函數,該函數使用Alamofire的GET函數返回一個基於自定義類的對象,該類保存此GET函數提供的各種輸出。
我不清楚這樣做的方式。
這是我的自定義類,它將包含有關響應的詳細信息:
import Foundation
class ResponsePackage {
var success = false
var response: AnyObject? = nil
var error: NSError? = nil
}
在另一個類中,我有以下功能:
func get(apiEndPoint: NSString) -> ResponsePackage {
let responsePackage = ResponsePackage()
Alamofire
.request(.GET, apiEndPoint)
.responseJSON {(request, response, JSON, error) in
responsePackage.response = JSON
responsePackage.success = true
responsePackage.error = error
}
return responsePackage
}
在return
執行之前,由於對服務器的調用未完成,因此返回nil
。 我知道我應該能夠用閉包來做這個,但我不知道如何構建它。
{}
之間的代碼相當於objective-C中的塊:這是異步執行的一大塊代碼。
您所做的錯誤是您放置return語句的位置:當您啟動請求時, {}
的代碼在框架收到響應之前不會執行,因此當達到return
語句時,可能仍然沒有響應。 你可以簡單地移動這條線:
return responsePackage
在閉包內部,所以func
只在收到響應時返回。 這是一種簡單的方法,但它並不是最佳的:您的代碼將在等待答案時陷入困境。 你可以做到這一點的最好方法是使用閉包。 這看起來像是這樣的:
func get(apiEndPoint: NSString, completion: (response: ResponsePackage) -> ()) -> Bool {
let responsePackage = ResponsePackage()
Alamofire
.request(.GET, apiEndPoint)
.responseJSON {(request, response, JSON, error) in
responsePackage.response = JSON
responsePackage.success = true
responsePackage.error = error
completion(response: responsePackage)
}
}
我舉一個例子,關注帶有閉包的 responseJSON問題:
按照這個小步驟:
首先,您可以在通用類中創建自定義類型(例如Constants.swift類):
typealias apiSuccess = (result: NSDictionary?) -> Void
typealias apiProgress = (result: NSDictionary?) -> Void // when you want to download or upload using Alamofire..
typealias apiFailure = (error: NSDictionary?) -> Void
然后在你的班上:
// Normal http request with JSON response..
func callJSONrequest(url:String, params:[String: AnyObject]?, success successBlock :apiSuccess,
failure failureBlock :apiFailure) {
Alamofire.request(.GET, url, parameters: params, encoding: ParameterEncoding.URL)
.responseJSON { response in
print("\(response.request?.URL)") // original URL request
//print(response.response) // URL response
//print(response.data) // server data
//print(response.result) // result of response serialization
if response.result.isSuccess {
let jsonDic = response.result.value as! NSDictionary
successBlock(result: jsonDic)
} else {
let httpError: NSError = response.result.error!
let statusCode = httpError.code
let error:NSDictionary = ["error" : httpError,"statusCode" : statusCode]
failureBlock(error: error)
}
}
}
}
func myCommonFunction() {
let myApiSuccess: apiSuccess = {(result: NSDictionary?) -> Void in
print ("Api Success : result is:\n \(result)")
// Here you can make whatever you want with result dictionary
}
let myApiFailure: apiFailure = {(error: NSDictionary?) -> Void in
print ("Api Failure : error is:\n \(error)")
// Here you can check the errors with error dictionary looking for http error type or http status code
}
var params :[String: AnyObject]?
let name : String! = "this is my name"
let id : String! = "000a"
params = ["name" : name, "id" : id]
let url : String! = "https://etc..."
callJSONrequest(url, params:params, success: myApiSuccess, failure: myApiFailure)
}
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.