Vb.net 如何解决';发送HTTP头后,服务器无法设置状态';尝试通过web api调用下载文件时出错?

Vb.net 如何解决';发送HTTP头后,服务器无法设置状态';尝试通过web api调用下载文件时出错?,vb.net,asp.net-web-api,webforms,download,asp.net-apicontroller,Vb.net,Asp.net Web Api,Webforms,Download,Asp.net Apicontroller,当我使用web api调用下载文件时,我可以轻松下载该文件。唯一的问题是,在错误日志中发送HTTP头后,我的get服务器无法设置状态。 很抱歉,如果这是一个可能重复的问题,但这里的答案都没有帮助我 <a href="/api/DownloadDocumentById?documentId=<%=doc.Id %>" download> <i class="fa fa-download text-

当我使用web api调用下载文件时,我可以轻松下载该文件。唯一的问题是,在错误日志中发送HTTP头后,我的get服务器无法设置状态。 很抱歉,如果这是一个可能重复的问题,但这里的答案都没有帮助我

<a href="/api/DownloadDocumentById?documentId=<%=doc.Id %>" download>
                                    <i class="fa fa-download text-primary"></i>
                                </a>


公共函数DownloadDocumentById(documentId为整数)
Dim文件=xxxxxxxx
Dim context=HttpContext.Current
context.Response.ContentType=document.Type
context.Response.OutputStream.Write(document.Content,0,document.Size)
context.Response.AddHeader(“内容处置”,Baselib.FormatContentDispositionHeader($“{document.Name}”))
context.Response.AddHeader(“上次修改”,DateTime.Now.ToLongDateString())
context.Response.Flush()
context.Response.End()
Return HttpStatusCode.OK//还尝试在不返回值的情况下创建子对象
端函数
如前所述,我可以轻松下载该文档,但在发送HTTP头后,IIS日志服务器仍无法设置状态。
再次抱歉,这是一个重复的问题。希望有人能帮助我。

首先,我认为您应该在开始编写实际输出/内容之前添加所有标题。对于缓冲流(这是我将要建议的),这应该没有什么区别,而且主要只是语义上的,但是由于在写入内容之前应该添加标题(内容总是最后一个),如果您决定使用非缓冲流,将来可能会避免类似的问题

因此,我建议您相应地重新订购代码:

context.Response.ContentType = document.Type

context.Response.AddHeader("Content-Disposition", Baselib.FormatContentDispositionHeader($"{document.Name}"))
context.Response.AddHeader("Last-Modified", DateTime.Now.ToLongDateString())

context.Response.OutputStream.Write(document.Content, 0, document.Size)
现在,如果使用非缓冲流,则在调用
OutputStream.Write()
时,内容将立即发送到客户端,因此,为了在以后设置HTTP结果,您需要确保整个响应都已缓冲,以便在内部请求(操作和控制器)之前不会发送已完成执行。这可以通过在输出任何内容之前设置为
True
来完成:

context.Response.BufferOutput = True

context.Response.ContentType = document.Type

'The rest of the code...
最后,您需要删除对
Response.Flush()
Response.End()
的调用,因为它们会提前清空缓冲区,并在您返回状态代码之前将所有内容写入客户端

新代码:

(...)

context.Response.BufferOutput = True

context.Response.ContentType = document.Type

context.Response.AddHeader("Content-Disposition", Baselib.FormatContentDispositionHeader($"{document.Name}"))
context.Response.AddHeader("Last-Modified", DateTime.Now.ToLongDateString())

Return HttpStatusCode.OK

首先也是最重要的,我认为在开始编写实际输出/内容之前,应该添加所有标题。对于缓冲流(这是我将要建议的),这应该没有什么区别,而且主要只是语义上的,但是由于在写入内容之前应该添加标题(内容总是最后一个),如果您决定使用非缓冲流,将来可能会避免类似的问题

因此,我建议您相应地重新订购代码:

context.Response.ContentType = document.Type

context.Response.AddHeader("Content-Disposition", Baselib.FormatContentDispositionHeader($"{document.Name}"))
context.Response.AddHeader("Last-Modified", DateTime.Now.ToLongDateString())

context.Response.OutputStream.Write(document.Content, 0, document.Size)
现在,如果使用非缓冲流,则在调用
OutputStream.Write()
时,内容将立即发送到客户端,因此,为了在以后设置HTTP结果,您需要确保整个响应都已缓冲,以便在内部请求(操作和控制器)之前不会发送已完成执行。这可以通过在输出任何内容之前设置为
True
来完成:

context.Response.BufferOutput = True

context.Response.ContentType = document.Type

'The rest of the code...
最后,您需要删除对
Response.Flush()
Response.End()
的调用,因为它们会提前清空缓冲区,并在您返回状态代码之前将所有内容写入客户端

新代码:

(...)

context.Response.BufferOutput = True

context.Response.ContentType = document.Type

context.Response.AddHeader("Content-Disposition", Baselib.FormatContentDispositionHeader($"{document.Name}"))
context.Response.AddHeader("Last-Modified", DateTime.Now.ToLongDateString())

Return HttpStatusCode.OK

非常感谢你!工作起来很有魅力。我按照你说的重新安排了代码,没有更多的IIS错误。谢谢你,先生@视觉的Vincent@arvind:很高兴我能帮忙!祝你的项目好运!万分感谢@非常感谢你!工作起来很有魅力。我按照你说的重新安排了代码,没有更多的IIS错误。谢谢你,先生@视觉的Vincent@arvind:很高兴我能帮忙!祝你的项目好运!万分感谢@视觉文森特