Need help w/escaping closures for API call


Hi, I'm new to programming and am working on an app based originally on Angela Yu's Clima app. I have my functions set up for the API call and am stuck on the escaping closures and passing in the correct arguments for them.

MappedResults is a separate struct that I set up for the relevant API data that I want to capture.


I think my confusion is around the myResults and MappedResults() but I'm not 100% on that.

(Once I figure this out, my next step will be to take that passed info and populate it into a tableview, which is why I'm using escaping closures).

Code Block
import UIKit
import CoreLocation
protocol APIManagerDelegate {
  func didUpdateAPIResults(inputMyResults: MappedResults)
  func didFailWithError(error: Error)
}
class APIManager {
   
  var myResults = MappedResults(
    locationName: "String",
    temperatureInF: 0,
    longitude: 0,
    latitude: 0
  )
   
  let dataURL = ""
  let myApiKey = ""
   
  var delegate: APIManagerDelegate?
   
  func fetchData(location: String, fetchDataCompletionHandler: @escaping (MappedResults) -> Void) {
     
 var urlComponents = URLComponents(string: dataURL)
    urlComponents?.queryItems = [
      URLQueryItem(name: "appId", value: myApiKey),
      URLQueryItem(name: "units", value: "imperial"),
      URLQueryItem(name: "q", value: location),
    ]
     
    self.performRequest(url: urlComponents?.url, performRequestCompletionHandler: {_ in
      fetchDataCompletionHandler(self.myResults)
    })
     
  }
  func performRequest(url: URL?, performRequestCompletionHandler: @escaping (MappedResults) -> Void) {
     
    guard let url = url else {print("Cannot Return URL Safely") ; return}
     
    let session = URLSession(configuration: .default)
     
    let task = session.dataTask(with: url) { data, response, error in
      guard let data = data else {print("Couldn't get back data from url task") ; return}
       
      guard let MappedResults = self.parseJSON(rawJsonData: data) else {print("Couldn't get mapped results") ; return}
       
      self.delegate?.didUpdateAPIResults(inputMyResults: MappedResults)
       
      if let e = error {
        print(e.localizedDescription)
      }
       
      performRequestCompletionHandler(MappedResults)
    }
    task.resume()
  }
   
  func parseJSON(rawJsonData: Data) -> MappedResults? {
    
    let decoder = JSONDecoder()
    do {
      let decodedAPIResults: APIResults =
        try decoder.decode(
          APIResults.self,
          from: rawJsonData)
       
      let myResults = MappedResults(
        locationName: decodedAPIResults.name,
        temperatureInF: decodedAPIResults.main.temp,
        longitude: decodedAPIResults.coord.lon,
        latitude: decodedAPIResults.coord.lat
      )
      return myResults
    } catch {
      delegate?.didFailWithError(error: error)
      return nil
    }
  }
}


Thanks



Answered by OOPer in 675962022
Can you be more specific?
What is the current issue with your code?
  • Does it cause some build-time errors and cannot run?

  • Or it runs but causes some runtime errors?

  • Or else, it runs without errors but shows unexpected results?


And you should better include all the relevant types when showing your code.
What are APIResults and MappedResults?
Please show the definitions of them.

One more, it is not recommended to use an initializer exactly the same as existing type names, as in your Line 47.
It should be lowercased mappedResults.

Accepted Answer
Can you be more specific?
What is the current issue with your code?
  • Does it cause some build-time errors and cannot run?

  • Or it runs but causes some runtime errors?

  • Or else, it runs without errors but shows unexpected results?


And you should better include all the relevant types when showing your code.
What are APIResults and MappedResults?
Please show the definitions of them.

One more, it is not recommended to use an initializer exactly the same as existing type names, as in your Line 47.
It should be lowercased mappedResults.

Thanks, your comments helped out a lot. I think the main issue I was concerned with was whether or not I was using the right info in the completion handlers. It currently runs and doesn't throw any errors.

Next time I post a question I'll be sure to include more info, and thanks for the tip on line 47. I'll try that and see if anything changes.

Need help w/escaping closures for API call
 
 
Q