如何在调用 HttpContext.Request 时避免 HttpException
本文关键字:HttpException Request HttpContext 调用 | 更新日期: 2023-09-27 17:58:47
所以 HttpContext.Request 如果在全局启动中调用,则会抛出
public HttpRequest get_Request()
{
if (this.HideRequestResponse)
{
throw new HttpException(SR.GetString("Request_not_available"));
}
return this._request;
}
这实际上是有记录的
如果在 HttpRequest 对象不可用时尝试使用此属性,ASP.NET 将引发异常。例如,在 Global.asax 文件的 Application_Start 方法或从 Application_Start 方法调用的方法中,情况将如此。此时尚未创建 HTTP 请求。
有没有办法检查 HttpContext.Request 是否处于可以在不引发异常的情况下检索的状态?实际上,我想编写一个TryGetRequest
帮助程序方法。
- 反思不是一种选择。它需要是一个公共 API。
- 我无权访问应用程序上下文。 这是通用日志记录代码。因此,在启动完成后设置一些标志不是一种选择
正如deoroll所观察到的,依靠 ASP.NET 应用程序生命周期来确定当前HttpRequest何时可用是合理的,实际上可能有必要。 通用日志记录代码可能至少依赖于对当前HttpContext
实例的HttpContext.Current
或其他一些引用。 如果该假设成立,则可以实现一个HttpModule
,该在BeginRequest
事件触发时在HttpContext.Items
集合中存储标志。 静态TryGetRequest
帮助程序方法可以测试该标志是否存在,以确定使用 HttpContext.Request
是否安全。
也许是这样的:
public class HttpRequestHelper : IHttpModule
{
private const string HttpRequestIsAvailable = "HttpRequestIsAvailable";
public static bool TryGetRequest(HttpContext context, out HttpRequest request)
{
request = null;
if (context != null)
{
if (context.Items.Contains(HttpRequestIsAvailable))
request = context.Request;
}
return (request != null);
}
#region IHttpModule
public void Dispose()
{
}
public void Init(HttpApplication context)
{
context.BeginRequest += context_BeginRequest;
}
private void context_BeginRequest(object sender, EventArgs e)
{
((HttpApplication)sender).Context.Items.Add(HttpRequestIsAvailable, true);
}
#endregion
}
该模块必须在 web.config 中注册(假设 IIS 7.0 集成管道(:
<system.webServer>
<modules>
<add name="HttpRequestHelper" type="Utility.HttpRequestHelper" />
</modules>
</system.webServer>
日志记录代码将使用帮助程序方法,如下所示:
HttpRequest request;
if (HttpRequestHelper.TryGetRequest(HttpContext.Current, out request))
LogWithRequest(request, message);
else
LogWithoutRequest(message);
该实现不依赖于私有 API 或反射。 它依赖于标志,但状态信息保留在HttpContext
实例中,并且封装得很好。
为什么不用 try、catch 块来包装对HttpContext.Request
的调用,然后你可以捕获异常并相应地修改你的行为。
不使用反射是不可能的