Swift关闭API连接

时间:2018-03-17 04:44:37

标签: swift api urlsession

如果我使用这种方式连接到API,这是否会创建连接会话?以及如何关闭它以便下次运行时不会花太多时间,因为有另一个会话打开了?!

do {
    let data = try String(contentsOf: url)
    if !data.isEmpty {
        // use data
    }
} catch {
    print("Log \(error)")
}

更新

我的会话将从API检索新闻,并根据这些新闻纬度和经度在地图上绘制标记。 API请求总是需要大约一秒钟,但在绘制之后,标记需要不同的时间。当我导航到另一个视图然后返回到地图视图时,应用程序向API发送新请求并生成新的响应新闻标记。每次我导航回地图时,绘制标记需要更多时间这些是应用程序从启动API请求到标记完全绘制所需的时差:

第一次拍摄:7秒

第二次拍摄:18秒

第3次拍摄:30秒

第四次拍摄:38秒

第五次拍摄:49秒

我尝试了task.suspend()task.cancel()session.invalidateAndCancel(),但结果仍然相同。

如何解决此时间问题?

func getData() {
    let urlString = URLFactory()
    DispatchQueue.global(qos: .background).async {
        // Set up the URL request
        guard let url = URL(string: urlString.getWebserviceURL()) else {
            NSLog("Log Error: cannot create URL")
            self.processData()
            return
        }
        let urlRequest = URLRequest(url: url)

        if self.task != nil {
            NSLog("Log suspend task")
            self.task!.suspend()
        }

        // make the request
        self.task = self.session.dataTask(with: urlRequest, completionHandler: {
            (data, response, error) in
            NSLog("Log start task")
            // check for any errors
            guard error == nil else {
                NSLog("Log error calling GET on webservice/getAllData: \(error!)")
                self.processData()
                return
            }
            // make sure we got data
            guard let responseData = data else {
                NSLog("Log Error: did not receive data")
                self.processData()
                return
            }
            // parse the result as JSON, since that's what the API provides
            do {
                guard let stringResponse = String(data: responseData, encoding: String.Encoding.utf8) else {
                    self.processData()
                    return
                }
                let json = JSON(parseJSON: stringResponse)
                if (json["data"].arrayObject != nil) {
                    self.parse(json: json)
                }
                self.processData()
            }
        })

        self.task!.resume()
    }
}

private func processData() {
    DispatchQueue.main.async {
        if(!self.newsObj.isEmpty) {
            self.drawMarker { () -> () in
                self.stopActivityIndicator()
                NSLog("Log Finished loading markers")
            }
        } else {
            self.showToast(message: "No data found")
        }
    }
}

private func parse(json: JSON) {
    newsObj.removeAll()
    for data in json["data"].arrayValue {
        // parse news data to newsObject
        newsObj.append(news)
    }
}

private func drawMarker(completion: (() -> ())) {
    if mapView != nil {
        mapView.clear()
        startActivityIndicator("Loading Markers...")
        for news in newsObj {
            let marker = GMSMarker()
            let listLatLng = news.getLatlong()
            for latlng in listLatLng {
                // Do stuff ...
                }
            }
            marker.map = self.mapView
        }
        completion()
    } 
}

1 个答案:

答案 0 :(得分:0)

除非url仅为本地文件,否则您应该不使用此方法。你应该在URLSession中这样做,这里是如何:

let task = URLSession().dataTask(with: URL.init(string: "")!, completionHandler: {data, response, error in
    if error != nil{
        print("Log \(error)")
        return //Stops the function
    }
    guard let data = data else{
        return
    }
    guard let stringResponse = String(data: data, encoding: String.Encoding.utf8) else{
        return
    }
    print("Log \(stringResponse)")
})

task.resume()

在上面的示例中,stringResponse将数据保存为URL中的字符串。

还要确保您使用的是HTTPS,而不是HTTP