Synchronous URL request on Swift 2

前端 未结 4 1567
难免孤独
难免孤独 2020-11-29 09:43

I have this code from here to do synchronous request of a URL on Swift 2.

  func send(url: String, f: (String)-> ()) {
    var request = NSURLRequest(URL:         


        
4条回答
  •  旧巷少年郎
    2020-11-29 09:53

    If you really wanna do it synchronously you can always use a semaphore:

    func send(url: String, f: (String) -> Void) {
        var request = NSURLRequest(URL: NSURL(string: url)!)
        var error: NSErrorPointer = nil
        var data: NSData
    
        var semaphore = dispatch_semaphore_create(0)
    
        try! NSURLSession.sharedSession().dataTaskWithRequest(request) { (responseData, _, _) -> Void in
            data = responseData! //treat optionals properly
            dispatch_semaphore_signal(semaphore)
        }.resume()
    
        dispatch_semaphore_wait(semaphore, DISPATCH_TIME_FOREVER)
    
        var reply = NSString(data: data, encoding: NSUTF8StringEncoding)
        f(reply)
    }
    

    EDIT: Add some hackish ! so the code works, don't do this in production code

    Swift 3.0+ (3.0, 3.1, 3.2, 4.0)

    func send(url: String, f: (String) -> Void) {
        guard let url = URL(string: url) else {
            print("Error! Invalid URL!") //Do something else
            return
        }
    
        let request = URLRequest(url: url)
        let semaphore = DispatchSemaphore(value: 0)
    
        var data: Data? = nil
    
        URLSession.shared.dataTask(with: request) { (responseData, _, _) -> Void in
            data = responseData
            semaphore.signal()
        }.resume()
    
        semaphore.wait(timeout: .distantFuture)
    
        let reply = data.flatMap { String(data: $0, encoding: .utf8) } ?? ""
        f(reply)
    }
    

提交回复
热议问题