Отслеживание прогресса закачки файла

xcode

#2

Вам нужно подписаться под делегат URLSession и тогда этот метод можете вставить в тот же файл, где идет ваша загрузка, только еще нужно будет реализовать протокол делегата

class YourClassName: ..., URLSessionDelegate {
    ...
    // ваш код с загрузкой

    // func urlSession(downloadTask) {
        ...
    }
}

#3

Здесь на сайте есть видео как раз по вашему вопросу - отображение (отслеживание) процесса закачки файла


#4

Там только через Alamofire реализовано


#5

Мой вариант вам не подошел?


#6

Да вот сейчас попробую, у меня вообще проблема в том что нужно информацию о ходе загрузки отправлять в кнопку, а кнопка в ячейке
А этот код весь в таблице


#7

#8

Это Вы мне скинули ?


#9

да. посмотрите как обновляется конкретная ячейка. если вы это имели в виду


#10

Мне получается нужно вот так сделать?

 func download(fileURL: URL) -> Bool  {
    if FileManager().fileExists(atPath: destination.path) {
        print("The file already exists at path")

   return true
        
    } else {
        

        URLSession.shared.downloadTask(with: fileURL, completionHandler: { (location, response, error)
            in

            guard
                let httpURLResponse = response as? HTTPURLResponse, httpURLResponse.statusCode == 200,
                let mimeType = response?.mimeType, mimeType.hasPrefix("audio"),
                let location = location, error == nil
               
                else { return }
            do {
                try FileManager.default.moveItem(at: location, to: self.destination)
                    print("file saved")
            } catch {
                print(error)
            }
        }).resume()
        
    return false }
}

func urlSession(_ session: URLSession, downloadTask: URLSessionDownloadTask, didFinishDownloadingTo location: URL) {
    print("downloaded")
}

func urlSession( _ session: URLSession, downloadTask: URLSessionDownloadTask, didWriteData bytesWritten: Int64, totalBytesWritten: Int64, totalBytesExpectedToWrite: Int64) {
    let progress = Float(totalBytesWritten) / Float(totalBytesExpectedToWrite)
    print(progress)
}

А сверху у меня вот так

class UnitTableViewController: UITableViewController, UnitCell, URLSessionDownloadDelegate {

#11

вот вам наглядный пример использования делегата

или вот пример по проще
https://www.ralfebert.de/ios-examples/networking/urlsession-background-downloads/


#12

Хорошо спасибо, постараюсь разобраться

Я потом смогу передать прогресс в кнопку в таком виде?

self.downloadButton.downloadPercent = downloadProgess

#13

если она находится в таблице - нет.
если вне таблицы - да.


#14

Она находится в ячейке, которая в таблице.
Я перепутал там вместо self должно быть cell поите


#15

только сперва вам нужно получить конкретную ячейку.
и не делайте это внутри замыкания, что бы не нагружать поиском ячейки процесс.


#16

Ячейка будет по нажатию на кнопку определяться


#17

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


#18

Так они все кнопкой скачать.

У меня сейчас все работает

Мне вот только хотелось бы прогресс закончи показать…
А из-за этого приходится весь код переписывать


#19

Я вроде начал разбираться с менеджером
У меня только такая проблема, мне нужно чтобы файл сохранялся в определенную директорию, а потом эту директорию нужно использовать для проигрывания
Как я понял код с директорией я переношу в менеджер?
Вот код

 var destination: URL {
     let documentsUrl = try! FileManager.default.url(for: .documentDirectory, in: .userDomainMask,      appropriateFor: nil, create: true)
    return documentsUrl.appendingPathComponent(fileURL!.lastPathComponent)
}

Вот код из менеджера для сохранения

func urlSession(_ session: URLSession, downloadTask: URLSessionDownloadTask, didFinishDownloadingTo location: URL) {
    debugPrint("Download finished: \(location)")
    try? FileManager.default.moveItem(at: location, to:destination)
}

Запускается менеджер таким образом

DownloadManager.shared.activate().downloadTask(with: fileURL!)
  1. Как мне в destination подставить fileURL?
  2. Как мне потом получившийся destination передать в следующий контролер? Или просто можно оставить эту часть кода в контроллере?

Спасибо


#20

наверное как-то так

let downloadManager = DownloadManager.shared
downloadManager.destination = fileURL!
downloadManager.activate().downloadTask(with: fileURL!)

#21

Так мне код он не дает такой оставить в download manager, он ругается на fileURL, но если его перед этим задать как nil, то все нормально только потом destination тоже nil равно

И destination не ровняется fileURL или я код неправильно понял?

не знаю насколько правильно, но я сделал вот так

let downloadManager = DownloadManager.shared
downloadManager.fileURL = fileURL!