Использование Response.End при форсировании PDF-загрузки
Недавно у нас возникла проблема, когда один из разработчиков изменил строку кода с помощью HttpResponse.End
на использование HttpApplication.CompleteRequest
, когда принудительно загружал PDF файл следующим образом:
qaru.site/info/286921/...
Это привело к тому, что некоторые PDF файлы не загрузились из-за неполадки в пространстве, поэтому код был изменен на использование HttpResponse.End
.
Однако, помогая моему коллеге, я проводил некоторые исследования, и я наткнулся на следующий вопрос:
Является ли Response.End() считающимся вредным?
Какие ссылки на:
https://blogs.msdn.microsoft.com/aspnetue/2010/05/25/response-end-response-close-and-how-customer-feedback-helps-us-improve-msdn-documentation/
Учитывая то, что задокументировано в сообщении в блоге MSDN, похоже, что использование HttpResponse.End
- неправильный подход, поэтому мне было интересно, требуется ли это или нужен ли более эффективный подход?
Ответы
Ответ 1
Вот фактический код из Response.End
:
public void End()
{
if (this._context.IsInCancellablePeriod)
{
HttpResponse.AbortCurrentThread();
return;
}
this._endRequiresObservation = true;
if (!this._flushing)
{
this.Flush();
this._ended = true;
if (this._context.ApplicationInstance != null)
{
this._context.ApplicationInstance.CompleteRequest();
}
}
}
ThreadAbortException
используется для управления потоком - в основном позволяет использовать Response.End
вместо return
. Но если вы хорошо разработали свой обработчик, вам может и не понадобится его, например. если после Response.End()
нет кода. Как правило, лучше не бросать исключение, если вы можете его избежать, так как он (как и все исключения) приведет к отключению стека и некоторой служебной нагрузке.
Возможно, вы можете написать свою собственную версию Response.End и выбрать и выбрать, какие строки кода выполнять на самом деле, например. возможно, вы хотите сбросить буфер и вызвать CompleteRequest, но вы не хотите генерировать исключение.
Ответ 2
Вот такой подход, который я использовал в прошлом
// Sends all currently buffered output
HttpContext.Current.Response.Flush(); to the client.
// Gets or sets a value indicating whether to send HTTP content to the client.
HttpContext.Current.Response.SuppressContent = true;
/* Causes ASP.NET to bypass all events and filtering in the HTTP pipeline
chain of execution and directly execute the EndRequest event. */
HttpContext.Current.ApplicationInstance.CompleteRequest();