Vapor загружать несколько файлов одновременно - PullRequest
4 голосов
/ 13 марта 2019

Я хочу загрузить несколько изображений в одном запросе POST. В настоящее время часть моего запроса, связанная с загрузкой файла, занимает один файл и выглядит так:

return try req.content.decode(File.self).flatMap(to: Image.self) { (file) in
    try file.data.write(to: URL(fileURLWithPath: DirectoryConfig.detect().workDir + localImageStorage + file.filename))
    return try Image(userID: user.requireID(), url: imageStorage + file.filename, filename: file.filename).save(on: req)
}

Это работает просто отлично. Теперь я попытался изменить .decode(File.self) на .decode([File].self) и выполнить цикл для всех файлов.
При попытке загрузить изображения с помощью параметра data[] в Postman, я получаю следующую ошибку:

Вложенное декодирование данных формы не поддерживается.

Как мне решить эту проблему?

1 Ответ

5 голосов
/ 13 марта 2019

Пример, приведенный ниже, работает хорошо, уже несколько раз тестировался ?

struct MyPayload: Content {
    var somefiles: [File]
}

func myUpload(_ req: Request) -> Future<HTTPStatus> {
    let user: User = try req.requireAuthenticated()
    return try req.content.decode(MyPayload.self).flatMap { payload in
        let workDir = DirectoryConfig.detect().workDir
        return payload.somefiles.map { file in
            let url = URL(fileURLWithPath: workDir + localImageStorage + file.filename)
            try file.data.write(to: url)
            return try Image(userID: user.requireID(), url: imageStorage + file.filename, filename: file.filename).save(on: req).transform(to: ())
        }.flatten(on: req).transform(to: .ok)
    }
}

Кстати, вы также можете объявить свою полезную нагрузку точно в параметрах функции

func myUpload(_ req: Request, _ payload: MyPayload) -> Future<HTTPStatus> {
    let user: User = try req.requireAuthenticated()
    let workDir = DirectoryConfig.detect().workDir
    return payload.somefiles.map { file in
        let url = URL(fileURLWithPath: workDir + localImageStorage + file.filename)
        try file.data.write(to: url)
        return try Image(userID: user.requireID(), url: imageStorage + file.filename, filename: file.filename).save(on: req).transform(to: ())
    }.flatten(on: req).transform(to: .ok)
}

единственная разница в объявлении конечной точкифункция на маршрутизаторе

router.post("upload", use: myUpload)

против

router.post(MyPayload.self, at: "upload", use: myUpload)

Затем в Postman загрузите ваши файлы, как это PostmanMultipleFiles

...