作为一款高人气且容易上手的分布式后台执行服务,支持多种数据库。在. net core 的环境中,由 Core 自带的 DI 管理着生命周期,免去了在 NF4.X 环境中配置的麻烦,真正做到开箱即用。
Hangfie 官方支持是 MsSql 和 redis,除此之外,可供选择的还有和。
在应用入口项目需要引用和特定持久库,比如使用了 MsSql 数据库的。
而在其他项目(比如 bll 层的项目),只需引用基础的就可以了。
- services.AddHangfire(x => x.UseSqlServerStorage("<connection string>"));
启动 Hangfire 服务和对应的 web 面板如下:
- app.UseHangfireServer(); //启动Hangfire服务
- app.UseHangfireDashboard(); //启动hangfire面板
细心的观众可能会发现,这两个方法都有可选参数,可以提供更多的配置。
- var jobOptions = new BackgroundJobServerOptions {
- Queues = new[] {
- "test",
- "default"
- },
- //队列名称,只能为小写
- WorkerCount = Environment.ProcessorCount * 5,
- //并发任务数
- ServerName = "hangfire1",
- //服务器名称
- };
- app.UseHangfireServer(jobOptions);
要处理的队列列表对于有多个服务器同时连接到数据库,Hangfire 会认为他们是分布式中的一份子。现实中不同服务器往往存在着差异,这个时候就需要合理配置服务器 (应用) 的处理队列,举两个例子:1. 对于服务器性能差异的处理,有 100 个 A 任务和 50 个 B 任务需要处理,假设 A 服务器的性能是 B 服务器的两倍,如果不配置队列,那么会平分任务给两个服务器。如果我们只让 B 服务器处理 B 任务,而 A 服务器同时处理两种任务,这样 B 就能减少一些压力。
- Queues
2. 对于服务器能力差异的处理,假设 A 服务器能处理 A 和 B 两种任务,B 服务器只能处理 B 任务(没有处理 A 任务的方法或对象),如果不配置队列,默认会让 B 也执行 A 任务,从而产生错误。反面一想,如果 A 服务器和 B 服务器都有共同的接口,B 服务器不实现接口的方法,发起一个专属于 A 服务器队列的任务,而 A 服务器通过注入实现接口的方法,可以达到传递任务的效果。
并发任务数,超出并发数将等待之前的任务完成默认的并发任务数是线程(cpu)的 5 倍,如果 IO 密集型任务多而 CPU 密集型的任务少,可以考虑调高并发任务数。
- WorkerCount
以上是我用到的,当然还有其他配置参数等着你去开发。
在实际生产中,我们可能不希望任何人都可以访问面板,或暂停执行某些任务,这时就需要重写面板的权限了。默认情况下,只有本地访问权限才能使用 Hangfire 仪表板。所以需要重写控制面板,以便远程访问。
- var options = new DashboardOptions {
- Authorization = new[] {
- new HangfireAuthorizationFilter()
- }
- };
- app.UseHangfireDashboard("/hangfire", options);
- public class HangfireAuthorizationFilter : IDashboardAuthorizationFilter
- {
- //这里需要配置权限规则
- public bool Authorize(DashboardContext context)
- {
- return true;
- }
- }
直接将任务加入到待执行任务队列
- Fire-and-forget
在当前时间后的某个时间将任务加入到待执行任务队列
- Delayed
周期性任务,每一个周期就将任务加入到待执行任务队列
- Recurring
顾名思义,继续执行任务
- Continuations
- using (var connection = JobStorage.Current.GetConnection())
- {
- var storageConnection = connection as JobStorageConnection;
- if (storageConnection != null)
- {
- //立即启动
- var jobId = BackgroundJob.Enqueue(()=>Console.WriteLine("Fire-and-forget!"));
- }
- }
当然,不仅仅只有静态方法可以执行,Hangfire 的任务也是支持. net core 的依赖注入的,会构造一个对象并执行对应的方法。
- BackgroundJob.Enqueue(i => i.SomeMethod(someParams))
- [Queue("test")]
- public void TestQueue()
- {
- }
对于非周期任务,只需要在执行的方法添加 Queue 的特性就能指定该任务让特定的队列服务器处理。
而周期任务,则需要先声明:
- RecurringJob.AddOrUpdate(() => Console.WriteLine("Recurring!"),Cron.Daily,queue:"test");
Hangfire 支持自定义过滤器, 可以对任务在创建时、执行中、执行后等等状态执行特定特定的操作。
- //特定方法过滤器
- [LogEverything]
- public static void Send() {
- }
- //全局过滤器
- GlobalJobFilters.Filters.Add(new LogEverythingAttribute());
hangfire 是一个不错的开源后台任务组件,很奇怪的是没有中文文档。最近几天,简单地用谷歌机翻修改了部分章节,如果哪位同行看完后有兴趣翻译,可以联系一下我。
文档在 github 的地址: https://github.com/jonechenug/Hangfire-Chinese-Doc
docker 运行并访问本地 8080 端口:
- docker run --restart always --name hangfire -d -p 8080:80 daocloud.io/koukouge/hangfirezhdoc
来源: http://www.cnblogs.com/chenug/p/6655636.html