web-dev-qa-db-fra.com

Comment télécharger un fichier dans Alamofire 4 et le sauvegarder dans le répertoire Documents?

J'essaie d'utiliser Alamofire4 pour Swift3. Je dois télécharger les fichiers .mp3 et les enregistrer dans le répertoire Documents. Le code actuel est comme ceci:

func downloadAudioFromURL(url: String, completion: ((_ status: ResponseStatus, _ audioLocalURL: URL?) -> Void)?) {


        let fileManager = FileManager.default
        let directoryURL = fileManager.urls(for: .documentDirectory, in: .userDomainMask)[0]
        let audioFullURL = String.ensureFullURLPath(url)


        alamoManager.download(audioFullURL)
            .validate { request, response, temporaryURL, destinationURL in

                var pathComponent = response.suggestedFilename!
                if pathComponent == "m4a.mp4" {
                    // Due to the old Android audio files without a filename
                    // Assign a unique name so audio files don't overwrite each other
                    pathComponent = "\(NSUUID().uuidString).mp4"
                }
                let localURL = directoryURL.appendingPathComponent(pathComponent)

                if response.statusCode == 200 {
                    completion?(.success, localURL)
                } else {
                    completion?(.failure, nil)
                }
                return .success
            }

            .responseJSON { response in
                debugPrint(response)
                print(response.temporaryURL)
                print(response.destinationURL)
        }
    }

Cependant, je ne peux pas accéder aux fichiers à partir de la localURL après la sauvegarde. J'ai également remarqué que la localURL sera exactement la même chose pour différents fichiers que j'essaie de télécharger (peut-être écrasent-ils?). E.g: file:///Users/testuser/Library/Developer/CoreSimulator/Devices/D4254AEA-76DD-4F01-80AF-F1AF3BE8A204/data/Containers/Data/Application/29755154-DD21-4D4C-B340-6628607DC053/Documents/file1.mp3

Des idées que je fais mal ici?

Edité mon code pour ressembler à ceci:

func downloadAudioFromURL(url: String, completion: ((_ status: ResponseStatus, _ audioLocalURL: URL?) -> Void)?) {

        let destination: DownloadRequest.DownloadFileDestination = { _, _ in
            var documentsURL = FileManager.default.urls(for: .documentDirectory, in: .userDomainMask)[0]

            documentsURL.appendPathComponent("Audiofile.mp3")
            return (documentsURL, [.removePreviousFile])
        }

        Alamofire.download(url, to: destination).response { response in

            if let localURL = response.destinationURL {

                completion?(.success, localURL)

            } else {

                completion?(.failure, nil)
            }

        }
}

Comment puis-je vérifier si m4a.mp4?

8
Kex

Pourquoi effectuez-vous .validate? Vous ne stockez aucune donnée après le téléchargement dans votre code actuel . Alamofire vous permet de stocker un fichier directement après le téléchargement:

let destination: DownloadRequest.DownloadFileDestination = { _, _ in
    let documentsURL = FileManager.default.urls(for: .documentDirectory, in: .userDomainMask)[0]
    let fileURL = documentsURL.appendPathComponent("pig.png")

    return (fileURL, [.removePreviousFile, .createIntermediateDirectories])
}

Alamofire.download(urlString, to: destination).response { response in
    print(response)

    if response.result.isSuccess, let imagePath = response.destinationURL?.path {
        let image = UIImage(contentsOfFile: imagePath)
    }
}

En passant, le chemin de téléchargement que vous indiquez dans la méthode download est l’URL locale du répertoire Documents et non l’URL d’un serveur.

12
ezcoding

Version Swift 3.x et Alamofire 4.x

Eh bien, l'exemple Alamofire publié par Alamofire lui-même contient des bogues. Comme fileURL renvoie Void, il ne peut pas être utilisé comme paramètre dans une instruction return.

Supprimez également .createIntermediateDirectories de la liste d'options de l'instruction return si vous ne voulez pas de répertoires pour le fichier que vous avez téléchargé.

MODIFIER
Si vous voulez connaître le type de fichier, il vous suffit de saisir le dernier composant et de convertir String en NSString en tant que NSString possèdent ces fonctionnalités.

//audioUrl should be of type URL
let audioFileName = String((audioUrl?.lastPathComponent)!) as NSString

//path extension will consist of the type of file it is, m4a or mp4
let pathExtension = audioFileName.pathExtension

let destination: DownloadRequest.DownloadFileDestination = { _, _ in
    var documentsURL = FileManager.default.urls(for: .documentDirectory, in: .userDomainMask)[0]

    // the name of the file here I kept is yourFileName with appended extension
    documentsURL.appendPathComponent("yourFileName."+pathExtension)
    return (documentsURL, [.removePreviousFile])
}

Alamofire.download("yourAudioUrl", to: destination).response { response in
            if response.destinationURL != nil {
                print(response.destinationURL!)
            }
        }

La sortie est

file:///Users/rajan/Library/Developer/CoreSimulator/Devices/92B4AB6E-92C0-4864-916F-9CB8F9443014/data/Containers/Data/Application/781AA5AC-9BE7-46BB-8DD9-564BBB343F3B/Documents/yourFileName.mp3

quel est le chemin réel de votre fichier où il est stocké.

7
Rajan Maheshwari

Objectif: les fichiers téléchargés du serveur tels que gif, pdf ou zip seront stockés dans le nom de dossier spécifié. 

Si vous voulez stocker votre propre structure de dossiers comme le nom est "ZipFiles"

appel . 

self downloadZipFileFromServer(downloadFolderName: "ZipFiles");

Les données Zip téléchargées sont stockées dans le document/ZiFiles/abc.Zip

cela crée juste un dossier à l'intérieur du document

func createFolder (folderName: String)

Alamofire 4
Swift 4
/******Download image/Zip/pdf  from the server and save in specific Dir********/
func downloadZipFileFromServer(downloadFolderName: string)
{
    let destination: DownloadRequest.DownloadFileDestination = { _, _ in
        var fileURL = self.createFolder(folderName: downloadFolderName)
        let fileName = URL(string : "www.xymob.com/abc.Zip")
        fileURL = fileURL.appendingPathComponent((fileName?.lastPathComponent)!)
        return (fileURL, [.removePreviousFile, .createIntermediateDirectories])
    }
    Alamofire.download("www.xymob.com/abc.Zip", to: destination).response(completionHandler: { (DefaultDownloadResponse) in                
        print("res ",DefaultDownloadResponse.destinationURL!);
    })
}        

func createFolder(folderName:String)->URL
{
    var paths: [Any] = NSSearchPathForDirectoriesInDomains(.documentDirectory, .userDomainMask, true)
    let documentsDirectory: String = paths[0] as? String ?? ""
    let dataPath: String = URL(fileURLWithPath: documentsDirectory).appendingPathComponent(folderName).absoluteString
    if !FileManager.default.fileExists(atPath: dataPath) {
        try? FileManager.default.createDirectory(atPath: dataPath, withIntermediateDirectories: false, attributes: nil)
    }
    let fileURL = URL(string: dataPath)
    return fileURL!
}
1
tikamchandrakar