我正在编写一个小型 node.js 应用程序,它从 HTML 表单接收多部分 POST 并将传入数据通过管道传输到 Amazon S3。强大的模块提供多部分解析,将每个部分公开为一个节点Stream。knox模块将PUT 处理到 s3。
var form = new formidable.IncomingForm()
, s3 = knox.createClient(conf);
form.onPart = function(part) {
var put = s3.putStream(part, filename, headers, handleResponse);
put.on('progress', handleProgress);
};
form.parse(req);
我正在通过socket.io向浏览器客户端报告上传进度,但很难让这些数字反映节点到 s3 上传的真实进度。
当浏览器到节点的上传几乎是瞬间发生时,就像节点进程在本地网络上运行时一样,进度指示器立即达到 100%。如果文件很大,即 300MB,进度指示器会缓慢上升,但仍然比我们的上行带宽允许的要快。在达到 100% 进度后,客户端然后挂起,大概是在等待 s3 上传完成。
我知道在内部putStream
使用 Node 的stream.pipe方法,但我不明白它是如何工作的细节。我的假设是节点尽可能快地吞噬传入的数据,并将其放入内存中。如果写入流可以足够快地获取数据,则很少有数据一次保留在内存中,因为它可以被写入和丢弃。但是,如果写入流很慢,就像这里一样,我们可能必须将所有传入的数据保留在内存中,直到可以写入为止。由于我们正在侦听data
读取流上的事件以发出进度,因此我们最终报告上传速度比实际速度快。
我对这个问题的理解是否接近标记?我该如何修复它?我需要对write
, drain
and感到沮丧和肮脏pause
吗?