Запустите JSON Request в фоновом режиме Swift 4 - PullRequest
0 голосов
/ 27 апреля 2018

Мне нужно запустить этот код в фоновом режиме, если это возможно. Я получаю запрос JSON, который иногда занимает некоторое время для загрузки (задержка на стороне URL-адреса сервера, а не на самом коде.).

Я хочу запустить приведенный ниже код в фоновом режиме, если это возможно. Есть идеи?

        var stockData: Data!
        var concatTickersString = ""


        for object in dataArray.reversed() {

            concatTickersString = concatTickersString + "," + object.symbol

        }

        let url = URL(string: "https://www.alphavantage.co/query?function=BATCH_STOCK_QUOTES&symbols=" + concatTickersString + "&apikey=IX58FUCXKD695JY0")

        do {
            stockData = try Data(contentsOf: url!)

            let json = try JSON(data: stockData)

            if let jsonArray = json["Stock Quotes"].array {

                for ticker in jsonArray.reversed() {

                    if(jsonArray.count != 0){

                        let stockTicker = ticker["1. symbol"].string!
                        let stockPrice = ticker["2. price"].string!

                        self.watchListArray.append(WatchlistData(tickerName: stockTicker, tickerPrice: Double(stockPrice)?.currency))

                    }

                }


                tableView.isHidden = false

            }


        } catch {
            print(error)     
        }

Это сервер JSON, который занимает много времени. Я не думаю, что это обязательно Данные (содержимое)

Я пытался использовать dispatch_async, но мне не повезло.

1 Ответ

0 голосов
/ 27 апреля 2018

Задержка вызвана тем, что Data(contentsOf:) является синхронным методом. Как говорится в документации 1004 *

Важно

Не используйте этот синхронный метод для запроса сетевых URL-адресов. Для сетевых URL-адресов этот метод может блокировать текущий поток на десятки секунд в медленной сети, что приводит к ухудшению работы пользователя, а в iOS может привести к прекращению работы вашего приложения. Вместо этого для нефайловых URL-адресов рассмотрите возможность использования метода dataTask (with: завершениемHandler :) класса URLSession. См. Выборка данных сайта в память для примера.

Как вы обнаружили в результате экспериментов, размещение этого метода в DispatchQueue.main.async не делает его асинхронным. Вместо этого следуйте инструкциям документации.

Это слегка измененный пример, найденный на Извлечение данных сайта в память :

func startLoad() {
    let url = URL(string: "https://www.example.com/")!
    let task = URLSession.shared.dataTask(with: url) { data, response, error in
        if let error = error {
            self.handleClientError(error)
            return
        }
        guard let httpResponse = response as? HTTPURLResponse,
            (200...299).contains(httpResponse.statusCode) else {
            self.handleServerError(response)
            return
        }
        if let data = data,
            let string = String(data: data, encoding: .utf8) {
            DispatchQueue.main.async {
                doSomething(with: string)
            }
        }
    }
    task.resume()
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...