2010-06-21 89 views
19

我有一個類DocumentGenerator,它包裝MemoryStream。所以我已經在班上實施了IDisposable如何在ASP.NET中實現文件下載時處理文件流?

我看不到我可以如何處置它。

這是我的當前代碼,執行在MVC文件下載:

using (DocumentGenerator dg = DocumentGenerator.OpenTemplate(path)) 
{ 
    /* some document manipulation with the 
     DocumentGenerator goes here ...*/ 

    return File(dg.GetDocumentStream(), "text/plain", filename); 
} 

該錯誤作爲前控制器已經完成了它的流被關閉/佈置。我怎樣才能確保我的資源在這種情況下妥善處置?

編輯:我的執行IDisposable此刻剛剛配置了MemoryStream。我知道這不是一個合適的實現,我只是用它作爲測試。有什麼不同,我可以在這裏做,使其工作?

public void Dispose() 
{ 
    _ms.Dispose(); 
    _ms = null; 
} 
+1

你能告訴我們IDisposable的實現嗎? – DHN 2010-06-21 11:58:53

+0

是否'_ms'與調用'GetDocumentStream'後相同? – 2010-06-21 12:21:30

+0

@Jordão:是的,這是正確的,因此問題。 – fearofawhackplanet 2010-06-21 15:05:13

回答

29

您不需要配置流。它將通過FileStreamResult.WriteFile方法進行處理。代碼摘錄自本課程:

public FileStreamResult(Stream fileStream, string contentType) : base(contentType) 
{ 
    if (fileStream == null) 
    { 
     throw new ArgumentNullException("fileStream"); 
    } 
    this.FileStream = fileStream; 
} 

protected override void WriteFile(HttpResponseBase response) 
{ 
    Stream outputStream = response.OutputStream; 
    using (this.FileStream) 
    { 
     byte[] buffer = new byte[0x1000]; 
     while (true) 
     { 
      int count = this.FileStream.Read(buffer, 0, 0x1000); 
      if (count == 0) 
      { 
       return; 
      } 
      outputStream.Write(buffer, 0, count); 
     } 
    } 
} 

請注意using。當您從控制器調用File(dg.GetDocumentStream(), "text/plain", filename)時,會調用將流存儲到公共屬性中的構造函數,該屬性將在渲染期間處理。

結論:你不必擔心配置流得到dg.GetDocumentStream()

+1

如果您的流來自另一個可處理的對象,如HttpWebResponse,那麼怎麼辦?我應該擔心處置HttpWebResponse還是假設它會收集垃圾? 示例 'var response =(HttpWebResponse)request.GetResponse(); return File(response.GetResponseStream(),「image/JPEG」);' – 2014-03-17 16:14:04

0

我想補充一下Darin has said,一定要注意這個概念是很重要的:

public Stream GetDownloadFile(...) 
{ 
    using (var stream = new MemoryStream()) { 
    return stream; 
    } 
} 

public Stream GetDownloadFile(...) 
{ 
    using (var generator = DocumentGenerator.OpenTemplate(path)) 
    { 
    // Document manipulation. 

    return File(generator.GetDocumentStream(), "text/plain", filename); 
    } 
} 

不管你是如何在你的方法使用它時,使用塊確保處置總是被調用,這是重要的,當你考慮使用using塊的結果作爲返回語句,它不會阻止它被處置....