繁体   English   中英

后台任务的全局异常处理

[英]Global Exception Handling for Background tasks

我一直在.NET核心API项目,我实现了一个基于这个例子中(在溶液中)后台任务在这里 我已经为我的 api 控制器使用了一些全局异常处理,并且根据要求,我必须删除所有 try catch 语句并改为提供简单的 HttpStatusCodes。

我需要通过创建一个从任何其他类继承的全局异常处理类来为我的后台任务/任务做同样的事情,并通过记录异常而不使系统崩溃来发挥它的“魔力”。 我还必须避免每个请求的 try/catch 语句。

到目前为止我的代码 HostedService

public class MyHostedService : CustomExceptionFilter, IHostedService
    {
        private Timer _timer;
        private readonly IServiceScopeFactory _scopeFactory;

        private readonly ILogger _logger;

        public SchedulerHostedService(IServiceScopeFactory scopeFactory)
        {
            _scopeFactory = scopeFactory;

            _logger = new LoggerManager();

        }
        public Task StartAsync(CancellationToken cancellationToken)
        {

            _logger.Info("Background Service is starting");
            _timer = new Timer(ExecuteTask, null, TimeSpan.Zero, TimeSpan.FromMinutes(30));
            return Task.CompletedTask;

        }

        private void ExecuteTask(object state)
        {
            _ = ExecuteTaskOperationAsync();
        }



        private async Task ExecuteTaskOperationAsync()
        {
            using (IServiceScope scope = _scopeFactory.CreateScope())
            {
                IAsyncTask service = scope.ServiceProvider
                    .GetRequiredService<IAsyncTask>();
                await service.CustomTaskAsync();
            }
        }

        public Task StopAsync(CancellationToken cancellationToken)
        {
            _logger.Info("Background Service is stopping");
            _timer?.Change(Timeout.Infinite, 0);
            return Task.CompletedTask;
        }

        public void Dispose()
        {
            _timer?.Dispose();
        }
    }

AsyncTask 实现

 internal interface IAsyncTask
    {
        Task CustomTaskAsync();
    }


    public class DbInternalOperation : CustomExceptionFilter, IAsyncTask
    {
        private readonly MyDbContext _context;

        private readonly ILogger _logger;
        public DbInternalOperation(MyDbContext context)
        {
            _context = context;

            _logger = new Logger();

        }

        public async Task CustomTaskAsync()
        {

            //All db logic to update some records based on date.           
           throw new Exception("Test");

                _logger.Info($"Scheduled operation started");

               //Some code for dbcontext 
                await _context.SaveChangesAsync();


                _logger.Info($"Scheduled operation finished");


        }

我的过滤器

public class CustomExceptionFilter : IExceptionFilter
{

    public void OnException(ExceptionContext context)
     {
        //Some logic for handling exceptions.
     }
}

并在我的 Startup.cs 中的服务

services.AddHostedService<MyHostedService>();
services.AddScoped<IAsyncTask, DbInternalOperation >();
services.AddMvc(options=>options.Filters.Add(new CustomExceptionFilter()));

我期待通过抛出异常让系统进入 'OnException' 方法并完成它的工作,但它没有。

我这里的结构有什么问题? 是否无法从继承自 IExceptionFilter 的任何服务中捕获任何异常? 如果有人可以提供一个异常过滤器的基本实现,用于我的后台任务而无需 try/catch,我将不胜感激。

过滤器和中间件仅适用于 MVC 管道,需要一个请求,否则管道不会启动。 IHostedService实现由Host (ASP.NET Core >= 3.0) 或WebHost (ASP.NET Core < 3.0) 触发,并且不在 MVC 管道中运行。

经典的try{}catch(Exception e)正是您在这里所需要的。

一些来源: https : //docs.microsoft.com/en-us/aspnet/core/fundamentals/middleware/ ? view =aspnetcore- 2.2 https://docs.microsoft.com/en-us/aspnet/core/mvc /controllers/filters?view=aspnetcore-2.2

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM