Charles Charles - 6 months ago 20
Swift Question

How to make a synchronous GET request

I have a method for GET request in my code:

func makeHTTPGetRequest(path: String, parameters: [String: AnyObject], completionHandler: (NSData?, NSURLResponse?, NSError?) -> Void) -> NSURLSessionTask {

let parameterString = parameters.stringFromHttpParameters()
let requestURL = NSURL(string:"\(path)?\(parameterString)")!

let request = NSMutableURLRequest(URL: requestURL)
request.HTTPMethod = "GET"
request.setValue("Bearer " + userInfoDefaults.stringForKey("accessToken")!, forHTTPHeaderField: "Authorization")

let session = NSURLSession.sharedSession()
let task = session.dataTaskWithRequest(request, completionHandler:completionHandler)
task.resume()

return task
}


That is called by an another method that populates a picker view on a specific scene:

func getAffiliateds() -> [String]? {
var affiliateds:[String] = []
makeHTTPGetRequest(baseURL + "affiliateds", parameters: [:], completionHandler: { (data, response, error) in
do {
affiliateds = try NSJSONSerialization.JSONObjectWithData(data!, options:[]) as! [String]
print (affiliateds)
}
catch { print("Error: \(error)") }
})
return affiliateds
}


I need to get all affiliateds from my webservice and then list it on the picker view. But when I debugged the code I noticed that affiliateds are first returned as a null array and then it is returned with the correct information. I need to return the array from getAffiliateds only when it has already received the data from the webservice. How can I make this?

Answer

You can't. Your getAffiliateds() cannot return a value dependent on the asynchronous code that it will run. That is the nature of asynchronous code. Instead, perform a callback of some sort in the completion handler when it is called:

makeHTTPGetRequest(baseURL + "affiliateds", parameters: [:], completionHandler: { (data, response, error) in
  do {
    affiliateds = try NSJSONSerialization.JSONObjectWithData(data!, options:[]) as! [String]
    print (affiliateds)
    // DO SOMETHING HERE
  }
}

A frequent strategy is for the caller to provide another completion handler which this completion handler will call.

Comments