2011-10-22 48 views
35

我正在創建一個應用程序,需要一些文件上傳並直接發送到S3。我寧願不要在我的服務器上安裝tmp文件,所以我使用了Knox模塊,並希望將來自Formidable的原始數據流通過Knox發送到S3。我一直在使用諾克斯使用此代碼下載文件做了類似的事情:從節點強大的文件上載訪問原始文件流

knox.downloads.get(widget.download).on('response',function(sres){ 
    res.writeHead(200, { 
     'Content-Type':'application/zip', 
     'Content-Length': sres.headers['content-length'], 
     'Content-Disposition':'attachment; filename=' + widget.download 
    }); 
    util.pump(sres, res); 
}).end(); 

現在我想(從瀏覽器到S3文件上傳)做的oposite方向類似的東西。

到目前爲止,我已經寫了一個事件處理程序來捕捉每一塊數據從文件,因爲它是被上傳:

var form = new formidable.IncomingForm(); 
form.onPart = function(part){ 
    if(!part.filename){ 
     form.handlePart(part); 
    }else{ 
     if(part.name == 'download'){ 
      // Upload to download bucket 
      controller.putDownload(part); 
     }else{ 
      // Upload to the image bucket 
      controller.putImage(part); 
     } 
     //res.send(sys.inspect(part)); 
    } 
} 
form.parse(req, function(err, fields, files){ 
    if(err){ 
     res.json(err); 
    }else{ 
     res.send(sys.inspect({fields:fields, files:files}), {'content-type':'text/plain'}); 
     //controller.createWidget(res,fields,files);    
    } 
}); 


controller.putDownload = function(part){ 
    part.addListener('data', function(buffer){ 
     knox.download.putStream(data,part.filename, function(err,s3res){ 
      if(err)throwError(err); 
      else{ 
       console.log(s3res); 
      } 
     }); 
    }) 
    knox.downloads.putStream(part, part.filename, function(err,s3res){ 

     if(err)throwError(err); 
     else{ 
      console.log(s3res); 
     } 
    }); 
} 

但數據事件只給我的緩衝區。那麼是否有可能捕獲流本身並推送到S3?

回答

17

你想要做的是覆蓋Form.onPart方法:

IncomingForm.prototype.onPart = function(part) { 
    // this method can be overwritten by the user 
    this.handlePart(part); 
}; 

厲害的默認行爲是編寫部分文件。你不想那樣。您想要處理'部分'事件以寫入knox下載。開始與這個:

form.onPart = function(part) { 
    if (!part.filename) { 
     // let formidable handle all non-file parts 
     form.handlePart(part); 
     return; 
    } 

然後打開諾克斯請求和處理自己的原始部分事件:

part.on('data', function(data) { 
    req.write(data); 
}); 
part.on('end', function() { 
    req.end(); 
}); 
part.on('error', function(err) { 
    // handle this too 
}); 

作爲獎勵,如果req.write(data)返回假,這意味着發送緩衝區已滿。你應該暫停Formidable解析器。當你從Knox流中獲得drain事件時,你應該恢復強大。

-2

您無法捕獲該流,因爲數據必須由Formidable進行轉換。您給出的bufferbuffer.length塊中的文件內容:這可能是一個問題,因爲查看Formidable的文檔,似乎直到文件完全上傳後才能可靠地報告文件大小,而Knox的put方法可能需要。

沒用過諾克斯這樣過,但你可能有一些運氣的東西是這樣的:

controller.putDownload = function(part){ 
    var req = knox.download.put(part.filename, { 
     'Content-Type': 'text/plain' 
    }); 
    part.addListener('data', function(buffer){ 
    req.write(buffer); 
    }); 
    req.on('response', function(res){ 
     // error checking 
    }); 
    req.end(); 
} 

有點不確定的迴應校驗位,但是....看你是否能擊敗那成形狀。此外,Streaming an octet stream from request to S3 with knox on node.js也有一個可能對你有用的寫法。

相關問題