-1

I am new in swift and creating a network call with below code but getting an "fatal error: unexpectedly found nil while unwrapping an Optional value" please help. Objective C version of this code is working fine for me

class func request(withUrlString urlString: String) -> NSMutableURLRequest
    {
        let request = NSMutableURLRequest(url: URL(string: urlString)!)
        request.addValue("application/json", forHTTPHeaderField:"Accept")
        request.httpMethod = "GET"
        request.timeoutInterval = 60
        return request
   }



class func send(_ request: URLRequest, completion callback: @escaping (_: Data, _: Error) -> Void)
    {
        if WebServiceManager.isInternetAvailable() == false
        {
            let data: NSData? = nil
            callback(data as! Data, NSError(domain:kNetworkErrorMeassage, code:0, userInfo:nil))
            return
        }

       // print("Request# \n URL : \(request.url?.absoluteString) \n Headers : \(request.allHTTPHeaderFields!.description) \n Request Method : \(request.httpMethod) \n Post body : \(request.httpBody ? try? JSONSerialization.jsonObject(withData: request.httpBody, options: []) : request.httpBody)\n")
      //  print("Request# \n URL : \(request.url?.absoluteString) \n Headers : \(request.allHTTPHeaderFields!.description) \n Request Method : \(request.httpMethod) \n Post body : \(request.httpBody ? String(data: request.httpBody!, encoding: String.Encoding.ascii) : request.httpBody)\n")

        UIApplication.shared.isNetworkActivityIndicatorVisible = true
        let dataTask : URLSessionDataTask? = URLSession.shared.dataTask(with: request) { (responseData, response, error) in

            UIApplication.shared.isNetworkActivityIndicatorVisible = false
            let httpResponce: HTTPURLResponse? = (response as? HTTPURLResponse)
            let responseStatusCode: Int? = httpResponce?.statusCode
            if responseStatusCode == 200 || responseStatusCode == 201 || responseStatusCode == 202
            {
                DispatchQueue.main.async(execute: {() -> Void in
                    callback(responseData!, error!)
               })
            }
            else
            {
                DispatchQueue.main.async(execute: {() -> Void in
                    let data: NSData? = nil
                    callback(data as! Data, error!)
                })
            }
        }
        dataTask?.resume()
    }
rmaddy
  • 314,917
  • 42
  • 532
  • 579
Vinay Kumar
  • 107
  • 1
  • 12

1 Answers1

1

responseData will be nil if the dataTask method encounters an error. In this case error will be non-nil. You should make sure to check for an error before force-unwrapping responseData in your callback.

Here’s a code sample:

class func send(_ request: URLRequest, completion callback: @escaping (_: Data, _: Error) -> Void) {
    let dataTask : URLSessionDataTask? = URLSession.shared.dataTask(with: request) { (responseData, response, error) in
        if let error = error {
            // handle error

        } else {
            // now we know responseData is non-nil

            UIApplication.shared.isNetworkActivityIndicatorVisible = false
            let httpResponce: HTTPURLResponse? = (response as? HTTPURLResponse)
            let responseStatusCode: Int? = httpResponce?.statusCode
            if responseStatusCode == 200 || responseStatusCode == 201 || responseStatusCode == 202 {
                DispatchQueue.main.async  {
                    callback(responseData!, nil)
               }
            } else {
                // ...
            }
        }
    }
}

The first thing that happens here is the error check. After that you can safely unwrap the optional responseData. Since error is nil in this case I changed the Error variable of your callback function to an optional.

I also used the trailing closure syntax for the Dispatch.main.async call as it makes it more readable.

Finally, in your else clause (which is not contained in my sample) you create a variable data which is nil only to force-cast it one line later... this will always crash. Please think again about what you want to achieve here.

Tom E
  • 1,530
  • 9
  • 17