Как использовать делегат URLSession с пользовательским классом

#ios #delegates #urlsession

#iOS #делегаты #urlsession

Вопрос:

Я привык создавать пользовательский класс для URLSession использования singleton. Итак, я использую его с URLSession делегатом в первый раз, и я запутался. Потому что метод делегата не вызывается!

Могу ли я узнать какое-либо решение? Я что-то пропустил?

И я просто хочу проверить, хорошо ли создавать пользовательский класс для URLSession ?

Вот мой код. Это мой пользовательский API для URLSession .

 
import UIKit

class CustomNetworkAPI {
    static let shared = CustomNetworkAPI()
    var session: URLSession?
    private var sessionDataTask: URLSessionDataTask?
    private var sessionDownloadTask: URLSessionDownloadTask?
    var cache: URLCache?
    
    private init() {}
    
    func downloadTaskForImage(_ url: URL, _ completionHandler: @escaping (Result<URL, Error>) -> ()) {
//        print(session.delegate)
        sessionDownloadTask = session?.downloadTask(with: url, completionHandler: { (url, response, error) in
            if let error = error {
                completionHandler(.failure(error))
                return
            }
            
            guard let url = url else {
                completionHandler(.failure(URLRequestError.dataError))
                return
            }
            
            completionHandler(.success(url))
        })
        
        sessionDownloadTask?.resume()
    }
}

 

И это пример кода (не целиком) VC с использованием api и делегата.

 import UIKit

class ViewController: UIViewController {
    override func viewDidLoad() {
        super.viewDidLoad()
        
        let api = CustomNetworkAPI.shared
        let config = URLSessionConfiguration.default

        api.session = URLSession(configuration: config, delegate: self, delegateQueue: nil)

        guard let url = URL(string: "...") else { return }
        
        api.downloadTaskForImage(url) { (result) in
            switch result {
            case .success(let url):
                print(url)
            case .failure(let error):
                print(error)
            }
        }
    }
}


extension ViewController: URLSessionDownloadDelegate {
    func urlSession(_ session: URLSession, downloadTask: URLSessionDownloadTask, didFinishDownloadingTo location: URL) {
        print("down load complete")
    }
    
    func urlSession(_ session: URLSession, downloadTask: URLSessionDownloadTask, didWriteData bytesWritten: Int64, totalBytesWritten: Int64, totalBytesExpectedToWrite: Int64) {
        print("ing")
    }
}

 

Ответ №1:

Мне чего-то не хватало, а именно приведенной ниже цитаты, которую я нашел в документах Apple.

Ваш объект URLSession не должен иметь делегата. Если делегат не назначен, используется системный делегат, и вы должны предоставить обратный вызов завершения для получения данных.

Итак, я попытался удалить блок обработчика завершения, и был вызван метод делегата.