加入收藏 | 设为首页 | 会员中心 | 我要投稿 李大同 (https://www.lidatong.com.cn/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 编程开发 > asp.Net > 正文

asp.net-web-api – 哪个优先级,ASP.NET Web Api 2.0中的Excepti

发布时间:2020-12-15 22:49:25 所属栏目:asp.Net 来源:网络整理
导读:我的web api 2.0中有一个全局ExceptionHandler,它处理所有未处理的异常,以便向api调用者返回一个友好的错误消息. 我也有一个全局ExceptionFilter,它处理一个非常特殊的异常在我的web api并返回一个具体的响应. ExceptionFilter由插件动态地添加到我的web api
我的web api 2.0中有一个全局ExceptionHandler,它处理所有未处理的异常,以便向api调用者返回一个友好的错误消息.
我也有一个全局ExceptionFilter,它处理一个非常特殊的异常在我的web api并返回一个具体的响应. ExceptionFilter由插件动态地添加到我的web api中,所以我不能在我的ExceptionHandler中执行它.

我想知道我是否在全球注册了ExceptionHandler和ExceptionFilter,哪一个将优先执行,首先执行?现在我可以看到ExceptionFilter正在执行ExceptionHandler之前.我也可以看到,在我的ExceptionFilter中,如果我创建一个响应,ExceptionHandler没有被执行.

假设这样做是安全的:

> ExceptionFilter在ExceptionHandler之前执行.
>如果ExceptionFilter创建一个响应,则ExceptionHandler将不被执行.

解决方法

我不得不通过System.Web.Http进行调试,以便找到我的问题的答案.所以答案是:

>可以安全地假设ExceptionFilters将在ExceptionHandler之前执行
>如果ExceptionFilter创建一个响应,ExceptionHandler将不会被执行.

为什么是这样的:

当您将ExceptionFilter注册为全局执行或用于控制器操作时,所有api控制器继承的ApiController基类都将将结果包装到一个ExceptionFilterResult中,并调用其ExecuteAsync方法.这是ApiController中的代码,它是这样做的:

if (exceptionFilters.Length > 0)
{
    IExceptionLogger exceptionLogger = ExceptionServices.GetLogger(controllerServices);
    IExceptionHandler exceptionHandler = ExceptionServices.GetHandler(controllerServices);
    result = new ExceptionFilterResult(ActionContext,exceptionFilters,exceptionLogger,exceptionHandler,result);
}

return result.ExecuteAsync(cancellationToken);

看看ExceptionFilterResult.ExecuteAsync方法:

try
{
    return await _innerResult.ExecuteAsync(cancellationToken);
}
catch (Exception e)
{
    exceptionInfo = ExceptionDispatchInfo.Capture(e);
}

// This code path only runs if the task is faulted with an exception
Exception exception = exceptionInfo.SourceException;
Debug.Assert(exception != null);

bool isCancellationException = exception is OperationCanceledException;

ExceptionContext exceptionContext = new ExceptionContext(
    exception,ExceptionCatchBlocks.IExceptionFilter,_context);

if (!isCancellationException)
{
    // We don't log cancellation exceptions because it doesn't represent an error.
    await _exceptionLogger.LogAsync(exceptionContext,cancellationToken);
}

HttpActionExecutedContext executedContext = new HttpActionExecutedContext(_context,exception);

// Note: exception filters need to be scheduled in the reverse order so that
// the more specific filter (e.g. Action) executes before the less specific ones (e.g. Global)
for (int i = _filters.Length - 1; i >= 0; i--)
{
    IExceptionFilter exceptionFilter = _filters[i];
    await exceptionFilter.ExecuteExceptionFilterAsync(executedContext,cancellationToken);
}

if (executedContext.Response == null && !isCancellationException)
{
    // We don't log cancellation exceptions because it doesn't represent an error.
    executedContext.Response = await _exceptionHandler.HandleAsync(exceptionContext,cancellationToken);
}

您可以看到先执行ExceptionLogger,然后执行所有ExceptionFilter,然后如果executionContext.Response == null,则执行ExceptionHandler.

我希望这是有用的!

(编辑:李大同)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

    推荐文章
      热点阅读