Node.js и Requestjs: передача потока Transform в Request.js в качестве файла для загрузки.

Я создаю zip-файл в памяти с помощью node-archiver ( https://github.com/archiverjs/node-archiver). Используя функцию конвейера, я передаю все в поток Transform. При необходимости я могу передать этот поток в файл, но я бы хотел, чтобы Request ( https://github.com/request) читал этот поток, поэтому мне не нужно переходить в файловую систему.

Ниже мой трансформационный поток называется bridge, Я не делаю ничего особенного в Transform (я считаю, что это также может быть поток PassThrough).

var archive = archiver('zip');
archive.pipe(bridge);
var r = request.post(url, function(err, res, body){ .... }
var form = r.form();
form.append('token', <some token>);
form.append('file', bridge, { "filename" : "package.zip", "contentType" : "application/zip" });
archive.append(<some string>, { "name": <some file name> });
archive.finalize();

Это не работает (кажется, file часть пуста). Однако, если я передаю свой поток Transform моста в поток записи файла - и после завершения потока - я создаю поток чтения для этого файла в операции с файлом формы, это работает. Конечно, потому что теперь у меня есть полностью сформированный файл и request могу прочитать это (и мне не нужен мост здесь, только обычный fs поток)

bridge.pipe(fs.createWriteStream(<myfile>));
var archive = archiver('zip');
archive.pipe(bridge);
bridge.on("finish", function(){
    var r = request.post(url, function(err, res, body){ .... }
    var form = r.form();
    form.append('token', <some token>);
    form.append('file', fs.createReadStream(<myfile>), { "filename" : "package.zip", "contentType" : "application/zip" });

}
archive.append(<some string>, { "name": <some file name> });    
archive.finalize();

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

1 ответ

Решение

У меня есть похожая проблема, и я обнаружил, что проблема не связана ни с nodejs, ни с requestjs.

Это ограничение по HTTP. Вы не можете загрузить файл без известной длины контента, которую вы не можете узнать из преобразования до того, как это будет сделано. Смотрите это: HTTP POST: требуется заголовок длины содержимого?

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

Другие вопросы по тегам