异常处理的奇怪行为

strange behaviour with exception handling

提问人:p.desterlich 提问时间:8/18/2023 最后编辑:p.desterlich 更新时间:8/21/2023 访问量:93

问:

我有一个 dotnet core 6 API,在异常处理方面存在非常奇怪的行为

  • 有一个异常中间件,它应该处理 API 调用中的所有异常(在应用启动中正确实例化)
  • 有一个过滤器可以进行一些常见的检查,如果不满足某些条件,就会引发异常
  • 控制器中有一个特定的 OnActionExecutionAsync 过程,用于进行特定检查,并在不满足条件时引发另一个异常
public class MyFilter : ActionFilterAttribute
{
    public override async Task OnActionExecutionAsync(ActionExecutingContext context, ActionExecutionDelegate next)
    {
        if (someCondition)
            throw new SomeException();

        await next();
    }
}

[MyFilter]
public class SomeController
{
    public override async Task OnActionExecutionAsync(ActionExecutingContext context, ActionExecutionDelegate next)
    {
        await base.OnActionExecutionAsync(context, next);
        
        if (someOtherCondition)
            throw new SomeOtherException();
        
        await next();
    }
}
    
public class ExceptionMiddleware
{
    private readonly RequestDelegate _next;

    public ExceptionMiddleware(RequestDelegate next)
    {
        _next = next;
    }

    public async Task InvokeAsync(HttpContext context, IRequestDataManager requestDataManager)
    {
        try
        {
            await _next(context);
        }
        catch (Exception ex)
        {
            // handle exception
            // if someCondition is met, i expect to have SomeException here
            // but instead if appears that SomeController.OnActionExecutionAsync ignore the exception and continue the execution
            // so, my problem is that:
            // if someCondition AND someOtherCondition are met i get SomeOtherException when i should get SomeException
            // if someCondition is met and someOtherCondition is NOT met i get no exception             
        }
    }   
}

问题是:

如果不满足筛选器中的条件,则会引发异常,但执行将返回到控制器 OnActionExecutionAsync 并从那里继续执行

如果我逐步调试代码,我可以看到过滤器内部引发的异常,但随后代码返回控制器并继续没有问题

如何在过滤器中引发异常并由异常中间件正确拦截该异常?

编辑:我已经建立了一个带有简单项目的 GitHub 存储库,该项目显示了问题:https://github.com/pdesterlich/webapitest

异常 ASP.NET-CORE-MIDDLEWARE

评论


答:

0赞 Ruikai Feng 8/21/2023 #1

问题通过过滤器的顺序来实现,您可以检查文档,并修改顺序

我根据您的代码尝试如下:

滤波器

public class SomeFilter: ActionFilterAttribute
{    
    public override async Task OnActionExecutionAsync(ActionExecutingContext context, ActionExecutionDelegate next)
    {

        var constants = new Constants();

        if (constants.GenerateException)
            throw new Exception("Filter Exception");

        await next();
    }
}

控制器:

[Route("api/test")]
[SomeFilter(Order = int.MinValue)]
public class SomeController: Controller
{
    public override async Task OnActionExecutionAsync(ActionExecutingContext context, ActionExecutionDelegate next)
    {
       
        var constants = new Constants();

        if (constants.GenerateException)
        {
            throw new Exception("Some Controller Exception");
             
        }
        await next();
    }
    
    [HttpGet]
    public async Task<IActionResult> GetScuole()
    {
        return Ok("Hello World");
    }
}

当我在不修改任何内容的情况下进行调试时:enter image description here

只需修改控制器中的条件:

if (!constants.GenerateException)

enter image description here

只需修改过滤器中的条件即可

if (!constants.GenerateException)

enter image description here