OperationQueue中的网络搜索+图像下载操作:操作vs URLSession的delegateQueue

时间:2017-05-13 18:07:55

标签: ios nsurlsession nsoperation nsoperationqueue nsurlsessiondownloadtask

我需要执行这种情况:

  • 用户提供了一些搜索参数,我应该使用这些参数来调用URL并解析其响应(我使用URLSessionDataTask)。
  • 该响应是一个JSON,可能包含多个图片网址,然后我应该调用下载(我使用尽可能多的URLSessionDownloadTask作为我获得的图片网址),然后将其显示在UITableView(每个单元格一个图像)。
  • 用户应该可以取消当前搜索以启动新搜索,因此之前的完整搜索+下载过程可能仍在进行中。

此外,对于数据任务(初始搜索),我使用URLSessionConfiguration.default,对于多个下载任务,我使用URLSessionConfiguration.background

初始搜索(数据任务)和设置N图像下载(N个下载任务)是串行的,这意味着我需要获得初始搜索的响应以启动图像下载。但是我需要将N个图像下载并发,因为一旦某个图像完成下载,我将在相应的单元格中显示每个图像。

另一方面,所有这些网络操作(搜索+下载)当然都需要是异步的。

我的问题:我看到URLSession有一个初始化程序,可以提供OperationQueue作为delegateQueue参数。关于这个选项,我想我应该这样做:

self.queue = OperationQueue()
self.queue.qualityOfService = .userInitiated
self.defaultSession = URLSession(configuration: configuration, delegate: nil, delegateQueue: queue)
self.backgroundSession = URLSession(configuration: backgroundConfiguration, delegate: self, delegateQueue: queue)

然后,当用户开始新搜索时,我应该可以致电self.queue.cancelAllOperations()

这是我的方案的正确方法吗?图像会同时下载吗?

我考虑的另一个选项是创建相同的OperationQueue,但不是将其作为delegateQueue传递给URLSession,而是将数据任务和下载任务建模为Operation并致电self.queue.addOperation

这两个选项之间的行为和表现有什么不同吗?哪一个应该适合我的场景?或者更好的是一种不同的方法(在这种情况下,哪一种方法)?

修改

我想到的其他选项是:每个单元都有一个对自己的URLSessionDownloadTask的引用,并在重用单元格时调用下载其图像,但在新的下载时要取消该任务执行,类似的事情:

var downloadTask: URLSessionDownloadTask?

func downloadImage(imageUrl: URL) {
    downloadTask?.cancel()

    let request = URLRequest(url: url)
    downloadTask = backgroundSession.downloadTask(with: request)
    downloadTask?.resume()
}

这里我没有使用操作队列,只是取消任务。这是正确和更好的选择吗?我应该在单元格出列时调用downladTask?.cancel()吗?

0 个答案:

没有答案