在ASP.NET Core RC2应用程序中定期运行后台任务

时间:2016-05-31 11:22:22

标签: c# asp.net asp.net-core quartz.net hangfire

我正在开发一个ASP.NET Core RC2应用程序。此应用程序需要定期调用某些任务,例如发送电子邮件或调用特定的业务逻辑。

我知道有一些第三方库,例如Hangfire或Quartz.NET,可以提供开箱即用的调度功能。但是我不认为其中任何一个当前都支持ASP.NET Core RC2。是否有任何其他可用的选项与ASP.NET Core RC2兼容?

如果没有,我想可能的选择是在单独的Windows服务中使用这些第三方库中的一个,然后可以定位支持的.NET版本。然后,该服务可以通过其Web API定期向ASP.NET应用程序发出请求,以便调用任务。

但是我不希望有单独的服务,因为它增加了移动部件的数量,并使我们的应用程序的部署变得复杂。

6 个答案:

答案 0 :(得分:9)

手动方法:

  • 创建一个包含长期运行代码的Service,最好是async
  • 使用暂停(也最好是while
  • 向服务添加async循环
  • 在具有Task.Run(() => ...的新线程中或在线程池中(或在旧版Thread中)调用服务类的长时间运行方法。
  • 在Startup.cs
  • 中创建该类的实例
  • 在Startup.cs
  • 中使用services.AddSingleton(MyServiceInstance);中的Configure(...

答案 1 :(得分:3)

  • 如果您要定位完整的.NET CLR,那么以前工作过的任何库都可以使用。在RC2中没有改变。 Azure WebJobs是另一种解决方案,除了您已经提到的解决方案之外。

  • 对于CoreCLR,我不知道任何已经兼容的框架。您可能必须提出自己的解决方案,或者通过在完整的.NET中使用所有计划的代码或者在完整的.NET中创建一个调用CoreCLR的小应用程序来分解您的应用程序。

    < / LI>

答案 2 :(得分:1)

我们使用一个简单的“任务运行器”应用程序,它接受命令行参数来确定要调用的Web / Windows服务。然后使用Windows任务计划程序调用“任务运行程序”应用程序。因此,服务是什么或者写入的技术并不重要。

答案 3 :(得分:1)

你总是可以给Quartz v3构建一个go。它已经在CoreCLR上运行,测试几乎已经过去了。您需要使用Visual Studio自己构建源代码。 See the v3 branch

目前最大的警告是不兼容的序列化,因为v2只能将二进制序列化为数据库(作业数据映射等),而v3仅支持JSON作为序列化格式。这个故事可能会改变,因为他们计划将BinaryFormatter带回来。

所以我要说,如果你在没有数据库持久性的情况下使用RAMJobStore,那么你应该很高兴。它可能比手工制作的解决方案更好。

答案 4 :(得分:0)

ASP.NET Core支持使用托管服务运行后台任务,请参阅此doc。它有一个名为IHostedService的接口,用于用户定义的托管服务。该接口为主机管理的对象定义了两种方法:

  • StartAsync(CancellationToken) - 在服务器启动并且触发IApplicationLifetime.ApplicationStarted后调用。
  • StopAsync(CancellationToken) - 在主机执行正常关闭时触发。

您还可以通过实现ExecuteAsync方法继承抽象类BackgroundService,如下所示:

protected override async Task ExecuteAsync(CancellationToken stoppingToken)
{
    stoppingToken.Register(() =>
            _logger.LogDebug($"Background task is stopping."));

    while (!stoppingToken.IsCancellationRequested)
    {
        _logger.LogDebug($"Background task doing work.");

        DoTask();

        await Task.Delay(TimeSpan.FromMinutes(1), stoppingToken);
    }

}

定义托管服务后,您需要将它们作为单身添加到ServiceCollection。然后这些后台任务将在asp.net核心应用程序中运行。

答案 5 :(得分:0)

考虑使用https://github.com/fluentscheduler/FluentScheduler

工作示例很简单

JobManager.AddJob(() => Console.WriteLine("My job!"),
                 (s) => s.ToRunEvery(5).Seconds());
相关问题