【发布时间】:2013-11-29 21:52:51
【问题描述】:
在 ASP.NET Web API 控制器中,我想返回一个图像。要流式传输图像,我需要MemoryStream。通常我会将它包装在using 语句中,以确保它在之后得到正确处理。但是,由于它在 Task 中异步执行,因此不起作用:
public class ImagesController : ApiController
{
private HttpContent GetPngBitmap(Stream stream)
{
var pngBitmapEncoder = new PngBitmapEncoder();
pngBitmapEncoder.Save(stream);
stream.Seek(0, SeekOrigin.Begin);
return new StreamContent(stream);
}
// GET api/images
public Task<HttpResponseMessage> Get(string id, string path)
{
//do stuff
return Task.Factory.StartNew(() =>
{
var stream = new MemoryStream(); //as it's asynchronous we can't use a using statement here!
{
var response = new HttpResponseMessage(HttpStatusCode.OK)
{
Content = GetPngBitmap(stream)
};
response.Content.Headers.ContentType =
new System.Net.Http.Headers.MediaTypeHeaderValue("image/png");
return response;
}
//how can I dispose stream???
});
}
}
【问题讨论】:
-
GetPngBitmap是什么类型,这在这种情况下很重要。当‘png bitmap’不再引用流时,dispose流是有效的。 -
在你调用
GetPnGBitmap()方法后调用Dispose on stream?或者使用 try finally 块并在 finally 中调用 Dispose,或者在您返回响应之前调用 Dispose。我不明白问题是什么?为什么你不能使用 using? -
Web API 托管层负责在写出响应后在此处处理流,因此您不必担心自己关闭流……还有方法调用 GetPngBitmap 做什么?是否将内容从文件复制到内存流?如果是,则无需再次创建内存流,只需将文件流直接提供给 Content 作为
StreamContent.. -
@Caramiriel:我试图处理它,但没有用。
-
感谢您的代码...是的,流将被 Web API 的主机层关闭,因此您无需明确地从您身边做任何事情...Web API 的托管层从您的内存流到网络流,然后关闭源流(您的内存流)...这对于所有响应来说通常是相同的行为..
标签: c# asp.net-web-api task-parallel-library using