Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/swift/16.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Swift URLSessionTaskDelegate从未在命令行工具中调用_Swift_Concurrency_Nsurlsession_Nsoperationqueue - Fatal编程技术网

Swift URLSessionTaskDelegate从未在命令行工具中调用

Swift URLSessionTaskDelegate从未在命令行工具中调用,swift,concurrency,nsurlsession,nsoperationqueue,Swift,Concurrency,Nsurlsession,Nsoperationqueue,我正在尝试编写我的第一个Swift命令行工具。该工具创建了一个网络请求,我想使用URLSessionTaskDelegate打印请求的进度 基本URL请求代码如下: 编辑:更新更完整的示例 class ApiSession: NSObject, URLSessionTaskDelegate { func makeRequest(request: URLRequest, callback: @escaping (Data?, URLResponse

我正在尝试编写我的第一个Swift命令行工具。该工具创建了一个网络请求,我想使用URLSessionTaskDelegate打印请求的进度

基本URL请求代码如下:

编辑:更新更完整的示例

class ApiSession: NSObject, URLSessionTaskDelegate {
    func makeRequest(request: URLRequest,
                     callback: @escaping (Data?, URLResponse?, Error?) -> Void) {
        let urlSession = URLSession(configuration: .default, delegate: self, delegateQueue: .main)
        let task = urlSession.dataTask(with: request, completionHandler: callback)
        task.resume()
        urlSession.finishTasksAndInvalidate()
    }
    
    func urlSession(_ session: URLSession, taskIsWaitingForConnectivity task: URLSessionTask) {
        print("WAITING")
    }
    
    func urlSession(_ session: URLSession, task: URLSessionTask, didCompleteWithError error: Error?) {
        print("TEST TEST")
    }
    
    func urlSession(_ session: URLSession, didBecomeInvalidWithError error: Error?) {
        print("BECAME INVALID")
    }
}

func main() throws {
    let apiSession = ApiSession()

    let request = URLRequest(url: URLComponents(string: "http://example.com/")!.url!)

    let sem = DispatchSemaphore(value: 0)
    apiSession.makeRequest(request: request) { (data, response, err) in
        if (err != nil) {
            print(err.debugDescription)
        }
        print(data)
        sem.signal()
    }

    // Code hangs here waiting for completion block to get called, but it never does when OperationQueue is main
    let _ = sem.wait(timeout: .distantFuture)
}

do {
    try main()
} catch (let error) {
    print("ERROR: \(error)")
}
当我使用基本的URLSession对象时,请求可以很好地完成。但是,如果我试图传入自己的URLSessionTaskDelegate来打印bytesSent,则调用永远不会发生。此外,如果我将我的
delegateQueue
设置为
OperationQueue.main
,则请求本身永远不会完成


我确信这里存在某种并发性问题,但我不知道从哪里开始调试。感谢您的帮助

您的CLI应用程序是否定义了RunLoop?如果没有RunLoop,它将退出,并且当主进程退出时,任何挂起的任务都将被释放。尝试添加以下内容:

while RunLoop.main.run(模式:.default,在:.distantFuture之前){

在主文件的末尾。

没有,但不幸的是,问题似乎与退出无关。由于从未调用请求完成块,因此代码挂起在信号量等待处,但当委托/操作队列不存在时,它会被很好地调用。我没有注意到信号量,它看起来正在阻塞主线程,这将阻止委托队列对其进行回叫。如果将delegateQueue更改为nil,是否会收到回调?