我使用以下代码在HttpResponseMessage
中返回一个字节数组:
using (WebResponse response = (HttpWebResponse)request.GetResponse())
{
byte[] bytes = ReadFully(response.GetResponseStream());
......
}
public static byte[] ReadFully(Stream input)
{
byte[] buffer = new byte[16*1024];
using (MemoryStream ms = new MemoryStream())
{
int read;
while ((read = input.Read(buffer, 0, buffer.Length)) > 0)
{
ms.Write(buffer, 0, read);
}
return ms.ToArray(); // This line throws OutOfMemory exception
}
}
在上一个OutOfMemory
语句中抛出了return ms.ToArray()
异常。
我需要将结果byte[]
设置为HttpResponseMessage.Content
。
答案 0 :(得分:2)
您应该直接返回流,而不是先将其读入内存。
public HttpResponseMessage CreateMessage(Stream input)
{
HttpResponseMessage result = new HttpResponseMessage(HttpStatusCode.OK);
result.Content = new StreamContent(input);
return result;
}
不要忘记设置适当的标题等。
...我需要将HttpResponseMessage中的字节数组写入文件
根据您的上一条评论,您更改了自己的问题,并希望采用其他方式。以下是从Web响应写入文件的示例。
public void writetoFile(HttpWebResponse response)
{
var inStream = response.GetResponseStream();
using (var file = System.IO.File.OpenWrite("your file path here"))
{
inStream.CopyTo(file);
}
}
答案 1 :(得分:1)
Igor发布了解决方案,以及处理流内容的正确方法。使用其中一个MVC辅助函数(如File(stream,contentype))或类StreamContent
等类将流内容直接发送到客户端,例如:
return File(myStream,myExcelContentTypeString);
或
return File(myStream,myExcelContentTypeString,"ReallyBigFile.xlsx");
错误的原因是OOM可能发生,因为内存太碎片而无法分配新对象。 MemoryStream将数据存储在缓冲区中。当它超过缓冲区限制时,它会分配一个容量增加一倍的新数据并复制旧数据。像这样复制250MB的数据将导致重新分配的批次,从而造成大量内存碎片。
可以通过在流的构造函数中指定所需的容量来避免这种情况。这将立即分配足够大的缓冲区。
尽管通过直接将其发送到浏览器来避免缓存此内容,情况会更好。