gpt4 book ai didi

asp.net - 通过 WebAPI 流式传输 SqlFileStream

转载 作者:行者123 更新时间:2023-12-01 02:34:53 24 4
gpt4 key购买 nike

我已经设置了一个支持 FILESTREAM 的 SQL 数据库,并且正在尝试通过 WebAPI 将使用 SqlFileStream 从数据库中检索到的文件流式传输到浏览器。

由于某种原因它不起作用,但我没有收到正确的错误消息。浏览器只是中止了连接,Fiddler 也没有显示任何有用的信息,而且在 VS 中似乎没有抛出任何错误。

public HttpResponseMessage Get(Guid id)
{
if(id == null || id == Guid.Empty)
return Request.CreateResponse(HttpStatusCode.BadRequest);

try
{
FileStreamContext fsc = null;
Document document = null;
using(var transaction = new TransactionScope())
using (var db = new MyEntities())
{
try
{
fsc = db.Database.SqlQuery<FileStreamContext>("SELECT [File].PathName() AS InternalPath, GET_FILESTREAM_TRANSACTION_CONTEXT() AS TransactionContext FROM Document WHERE id={0}", id).First();
}
catch (Exception e)
{
Debug.Print(e.ToString());
}

document = db.Documents.Where(doc => doc.ID == id).Single();

var fileStream = new SqlFileStream(fsc.InternalPath, fsc.TransactionContext, FileAccess.Read);

HttpResponseMessage response = new HttpResponseMessage();
response.Content = new StreamContent(fileStream);
//response.Content.Headers.ContentDisposition = new ContentDispositionHeaderValue("attachment");
//response.Content.Headers.ContentDisposition.FileName = document.FileName;
response.Content.Headers.ContentType = MediaTypeHeaderValue.Parse(document.ContentType);
return response;
}
}
catch (Exception e)
{
return Request.CreateResponse(HttpStatusCode.BadRequest);
}
}

我怀疑 TransactionScope 提前关闭可能是个问题?不确定为什么我没有收到任何错误消息。

通过 WebApi 流式传输 SqlFileStream 的正确方法是什么?

最佳答案

不是将内容设置为 StreamContent,您是否尝试读取 Controller 中的 fileStream,将其放入 byte 数组中,然后使用 ByteArrayContent 设置内容?

var fileStream = new SqlFileStream(fsc.InternalPath, fsc.TransactionContext, FileAccess.Read);
byte[] fileContent = fileStream.ReadFully(); // you will need to implement ReadFully
HttpResponseMessage response = new HttpResponseMessage();
response.Content = new ByteArrayContent(fileContent);

对于 ReadFully 实现,here is a link to a Jon Skeet method我用过的。

而且我怀疑您关于过早关闭连接的说法是正确的。您将 DbContext/ObjectContext 很好地包裹在 using block 中,但我认为这就是问题所在。该上下文在 Controller 返回 HttpResponseMessage 后被释放,但响应只能访问流——它仍然需要读取流并将其转换为 byte[] 在传递回浏览器或客户端之前。当您使用 MemoryStream 等时,这通常会自动发生,因为框架仍然可以访问流以读取其内容。但在这种情况下,您将在读取流之前处理 SQL 连接。

另一种解决方案是为您的 DbContext 使用依赖注入(inject),而不是在操作方法中更新它。如果您将 IoC 容器设置为在 HTTP 请求结束时自动处理上下文,那么当框架将 StreamContent 转换为 时,它应该仍然可用(未处理) byte[] 并通过网络将其推回。

关于asp.net - 通过 WebAPI 流式传输 SqlFileStream,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/18129311/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com