MVC ASP.NET 中的异步错误控制器
本文关键字:错误 错误控制 控制器 异步 ASP NET MVC | 更新日期: 2023-09-27 18:34:46
谁能帮我让一个异步错误控制器在 ASP MVC 中工作。我让它在没有异步的情况下工作,但这似乎不对。我开始使用的代码如下:
void Application_Error(object sender, EventArgs e)
{
Exception exception = Server.GetLastError();
// A good location for any error logging, otherwise, do it inside of the error controller.
// Clear the error, otherwise, we will always get the default error page.
Server.ClearError();
Response.Clear();
Response.TrySkipIisCustomErrors = true;
var code = (exception is HttpException) ? (exception as HttpException).GetHttpCode() : 500;
var routeData = new RouteData();
routeData.Values.Add("controller", "Error");
routeData.Values.Add("action", "index");
IController errorController = ClassFactory.Resolve<ErrorController>();
errorController.Execute(new RequestContext(new HttpContextWrapper(Context), routeData));
}
我的错误控制器的方法签名如下:
[AllowAnonymous]
public ActionResult Index(int code = 500)
{
如果我使错误控制器方法异步,则 Application_Error 中的 Execute 方法会引发异常"异步操作方法'index'返回无法同步执行的任务"。
我最有希望的尝试之一是转移请求。这在 applicaiton_error 方法中使用以下代码:
var code = (exception is HttpException) ? (exception as HttpException).GetHttpCode() : 500;
var headers = new NameValueCollection
{
{"ErrorUrl", Context.Request.RawUrl},
{"ErrorCode", code.ToString()}
};
Context.Server.TransferRequest("~/error", false, null, headers, true);
这运行良好且异步,我可以在请求标头中传递错误数据。不幸的是,Server.TransferRequest 调用丢失了有关当前登录用户的详细信息,并且用户将在错误页面上显示为已注销。用户登录代码当前与VS2013模板相同(不是旧表单身份验证(。保留用户参数似乎不起作用。
有没有人让这样的异步控制器工作?
或
有谁知道如何解决ASP身份在转移请求中丢失的问题?
相关问题包括Application_Error使用前缀异步时处理程序不会触发,其解决方案比不使用异步(一次使用两个线程(更糟糕。还有另一个与我类似的问题,但没有转移请求。
Context.Server.TransferRequest 是解决问题的正确方法。此函数通过整个 IIS 管道发送以下请求。我丢失ASP标识的原因是它存储在会话中。会话使用 Cookie 链接到客户端。饼干位于标题中。
而不是代码:
var code = (exception is HttpException) ? (exception as HttpException).GetHttpCode() : 500;
var headers = new NameValueCollection
{
{"ErrorUrl", Context.Request.RawUrl},
{"ErrorCode", code.ToString()}
};
Context.Server.TransferRequest("~/error", false, null, headers, true);
我已经让它与:
var code = (exception is HttpException) ? (exception as HttpException).GetHttpCode() : 500;
var headers = Request.Headers;
headers.Add(new NameValueCollection
{
{"ErrorUrl", Context.Request.RawUrl},
{"ErrorCode", code.ToString()}
});
Context.Server.TransferRequest("~/error", false, null, headers, true);
主要区别在于我传递了当前请求的标头,其中包含链接到会话的cookie。这可以防止丢失 ASP.NET 标识。