1

When I'm requesting API from my code I got response after 4-6sec which is way too long. From Postman I'm getting response after 120ms. Is that something in my code goes wrong? here is my code, I'm checking time between those two prints:

func makeUrlRequest<T: Codable>(_ request: URLRequest, resultHandler: @escaping (Result<T, RequestError>) -> Void) {
        var req = request
        req.addValue("application/json", forHTTPHeaderField: "Content-Type")
        req.addValue("application/json", forHTTPHeaderField: "Accept")
        let config = URLSessionConfiguration.default
        let urlSession = URLSession(configuration: config, delegate: self, delegateQueue: .main)
        print("Request: start at: \(Date())") //Request: start at: 2021-04-09 06:53:32 +0000
        let urlTask = urlSession.dataTask(with: req) { data, response, error in
            print("Request: finished at: \(Date())") //Request: finished at: 2021-04-09 06:53:36 +0000
            DispatchQueue.main.async {
                guard error == nil else {
                    resultHandler(.failure(.clientError))
                    return
                }

                guard let response = response as? HTTPURLResponse, 200...299 ~= response.statusCode else {
                    resultHandler(.failure(.serverError))
                    return
                }

                guard let data = data else {
                    resultHandler(.failure(.noData))
                    return
                }

                guard let decodedData: T = self.decodedData(data) else {
                    resultHandler(.failure(.dataDecodingError))
                    return

                }
                
                resultHandler(.success(decodedData))
            }
        }

        urlTask.resume()
    }
Gorthez
  • 391
  • 3
  • 12
  • You are creating the URLSession incorrectly. It should be a persistent instance, not a local, and it should not have a delegate, because you are using a completion handler. – matt Apr 09 '21 at 07:16
  • @matt I'm using delegate to bypass cert verification (just for now). About initalization, I've moved init of URLSession to class init but there is still delay – Gorthez Apr 09 '21 at 07:31

1 Answers1

1

Instead of

let urlSession = URLSession(configuration: config, delegate: self, delegateQueue: .main)
print("Request: start at: \(Date())") //Request: start at: 2021-04-09 06:53:32 +0000
let urlTask = urlSession.dataTask(with: req) { data, response, error in...

You should use

let task = URLSession.shared.dataTask(with: req) { (data, response, error) in...

EDIT:

I see that you would like to use a delegate. In that case you shouldn't use a completion handler but instead add the delegate methods:

func urlSession(_ session: URLSession, dataTask: URLSessionDataTask, didReceive data: Data)
func urlSession(_ session: URLSession, task: URLSessionTask, didCompleteWithError error: Error?)

Check out Apple's documentation for more info.

whyp
  • 603
  • 5
  • 14
  • 1
    Not meaning to be critical but this is exactly what I said in my comment: your creation of the url session was wrong. Either use a delegate or use a completion handler; don't try to mix them together. – matt Apr 09 '21 at 19:34
  • @matt I totally agree. I felt though that the OP needed a more elaborate answer and a stronger nudge in the right direction. It would have been better if I referred to your comment in my answer. Thank you for your awesome books, "Programming iOS 5" got me started back in 2012. – whyp Apr 09 '21 at 23:39
  • No criticism was intended! I was actually trying to get the OP to see that the answer had already been given, if one is willing to listen. :) Many thanks for nice comment. – matt Apr 09 '21 at 23:43