gpt4 book ai didi

swift 4 : How to asynchronously use URLSessionDataTask but have the requests be in a timed queue?

转载 作者:可可西里 更新时间:2023-11-01 01:59:34 24 4
gpt4 key购买 nike

基本上我有一些 JSON 数据,我希望从一堆 URL 中检索(全部来自同一主机),但是我只能大约每 2 秒至少请求一次此数据,并且一次只能请求一个,否则我会被服务器“时间禁止”。正如您将在下面看到的;虽然 URLSession 非常快,但当我有大约 700 个 url 需要通过时,它也会让我几乎立即被禁止。

我将如何在 URLSession 中创建一个队列(如果它的功能支持它)并让它与我的主线程异步工作;它是否在自己的线程上连续工作,并且仅在完成上一个请求后 2 秒后才尝试队列中的每个项目?

for url in urls {
get(url: url)
}


func get(url: URL) {
let session = URLSession.shared
let task = session.dataTask(with: url, completionHandler: { (data, response, error) in

if let error = error {
DispatchQueue.main.async {
print(error.localizedDescription)
}
return
}
let data = data!

guard let response = response as? HTTPURLResponse, response.statusCode == 200 else {
DispatchQueue.main.async {
print("Server Error")
}
return
}
if response.mimeType == "application/json" {
do {
let json = try JSONSerialization.jsonObject(with: data) as! [String: Any]
if json["success"] as! Bool == true {
if let count = json["total_count"] as? Int {
DispatchQueue.main.async {
self.itemsCount.append(count)
}
}
}
} catch {
print(error.localizedDescription)
}
}
})
task.resume()
}

最佳答案

递归解决这个问题最好

import Foundation
import PlaygroundSupport

// Let asynchronous code run
PlaygroundPage.current.needsIndefiniteExecution = true

func fetch(urls: [URL]) {

guard urls.count > 0 else {
print("Queue finished")
return
}

var pendingURLs = urls
let currentUrl = pendingURLs.removeFirst()

print("\(pendingURLs.count)")

let session = URLSession.shared
let task = session.dataTask(with: currentUrl, completionHandler: { (data, response, error) in
print("task completed")
if let _ = error {
print("error received")
DispatchQueue.main.async {
fetch(urls: pendingURLs)
}
return
}

guard let response = response as? HTTPURLResponse, response.statusCode == 200 else {
print("server error received")
DispatchQueue.main.async {
fetch(urls: pendingURLs)
}
return
}
if response.mimeType == "application/json" {
print("json data parsed")
DispatchQueue.main.async {
fetch(urls: pendingURLs)
}
}else {
print("unknown data")
DispatchQueue.main.async {
fetch(urls: pendingURLs)
}
}
})

//start execution after two seconds
Timer.scheduledTimer(withTimeInterval: 2, repeats: false) { (timer) in
print("resume called")
task.resume()
}
}

var urls = [URL]()
for _ in 0..<100 {
if let url = URL(string: "https://google.com") {
urls.append(url)
}
}

fetch(urls:urls)

关于 swift 4 : How to asynchronously use URLSessionDataTask but have the requests be in a timed queue?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/47694633/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com