Cancelling an Alamofire Request Wrapped In NSOperation Causes Multiple KVO?

戏子无情 提交于 2019-12-03 08:40:30

I don't find the multiple KVN behavior you describe as that surprising. There's nothing in the documentation that says that when it cancels all operations, that a single KVN on operations will result. In fact, one might safely infer that the behavior you describe should be expected (because it doesn't preemptively kill all of those worker threads, but rather sends a cancel message to each, and each operation is responsible for responding to that in its own time; and I wouldn't expect operations to be updated until the operation finally actually finishes).

Personally, I would advise retiring this observer pattern entirely. Your code should not be contingent upon whether NSOperationQueue removes all of operations at once or not. I would instead suggest that you instead rely upon your existing downloadImageCompletionHandler closure, calling it whether the request completed or not. Just have the closure look at the error object to figure out whether it was canceled or whether it failed for some other reason.


If your intent is to know when all of these operations are done, I wouldn't rely on operations KVN. Instead, I might create a completion operation, dependent upon all of those other requests:

let completionOperation = NSBlockOperation() {                    // create completion operation
    // do whatever you want here
}

for imgLink in imgLinks {
    let operation = DownloadImageOperation(URLString: imgLink) { responseObject, error in
        if error != nil {
            if error!.code == NSURLErrorCancelled && error!.domain == NSURLErrorDomain {
                println("everything OK, just canceled")
            } else {
                println("error=\(error)")
            }
        }
        if responseObject != nil {
            println("\(responseObject?.absoluteString) downloaded.")
        }
    }

    completionOperation.addDependency(operation)                 // add dependency

    testAlamofireObserver!.queue.addOperation(operation)
}

NSOperationQueue.mainQueue().addOperation(completionOperation)   // schedule completion operation on some other queue (so that when I cancel everything on that other queue, I don't cancel this, too)
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!