C#使用Topshelf框架和Quartz开发处理定时任务的Windows服务程序

  • 背景
  • 依赖
  • C#代码示例
  • 任务调度的配置文件
  • 测试
  • 服务安装、启动、停止、卸载

背景

有些业务是运行在后台,需要界面,但需要开机就自动运行很适合以Windows服务的形式部署,在.net领域为了简化Windows服务的开发最为常用的是使用Topshelf框架。简直就是傻瓜式的就可以把一个控制台程序转为一个Windows服务程序,而且服务的安装、启动、停止、卸载还非常简单。而Windows服务程序中实现的大多数业务都是持续定时触发的。通常就是任务调度程序,而业界最流行的任务调度框架就是Quartz,无论是java还是.net此框架都是实现任务调度的不二之选。本文就重点介绍一下这个框架的配合使用开发处理定时任务的Windows服务。

依赖

1、TopShelf:需要依赖Topshelf.dll,请自行下载。
2、Quartz:需要依赖Common.Logging.Core.dll、Common.Logging.dll、Quartz.dll,请自行下载。

C#代码示例

1、任务实现代码,就是定时任务要执行的代码,任务类要实现Quartz.IJob接口的Execute方法。
在解决方案中新建一个类库项目,命名为Wongoing.Jobs,并添加对Quartz.dll的引用,在此项目中添加一个类ServiceMonitorJob.cs,如下:

using System;
using System.Collections.Generic;
using System.Text;
using Quartz;namespace Wongoing.Jobs
{/// <summary>/// 服务监控任务类,主要通过心跳完成服务运行状态的监控/// </summary>public class ServiceMonitorJob : IJob{public void Execute(IJobExecutionContext context){Console.WriteLine("服务监控...");}}
}

2、Windows服务实现代码。Windows服务类要实现Topshelf.ServiceControl和Topshelf.ServiceSuspend接口的方法。
在解决方案下,新建一个控制台项目,命名为BTSDataService,设为启动项目,并在控制台项目中添加对Wongoing.Jobs项目、Topshelf.dll、Common.Logging.Core.dll、Common.Logging.dll、Quartz.dll的引用。然后在控制项目中添加一个类ServiceRunner.cs,代码如下:

using System;
using System.Collections.Generic;
using System.Text;
using Topshelf;
using Quartz;
using Quartz.Impl;namespace BTSDataService
{public sealed class ServiceRunner : ServiceControl, ServiceSuspend{private readonly IScheduler scheduler;  //定义任务调度器/// <summary>/// 构造方法/// </summary>public ServiceRunner(){scheduler = StdSchedulerFactory.GetDefaultScheduler();      //从任务调度工厂获取默认的任务调度器}/// <summary>/// 服务启动/// </summary>/// <param name="hostControl"></param>/// <returns></returns>public bool Start(HostControl hostControl){try{this.scheduler.Start();Console.WriteLine("服务已启动...");return true;}catch(Exception ex){Console.WriteLine("服务启动失败:" + ex.Message);return false;}}/// <summary>/// 服务继续/// </summary>/// <param name="hostControl"></param>/// <returns></returns>public bool Continue(HostControl hostControl){try{this.scheduler.ResumeAll();Console.WriteLine("服务已继续...");return true;}catch (Exception ex){Console.WriteLine("服务继续失败:" + ex.Message);return false;}}/// <summary>/// 服务暂停/// </summary>/// <param name="hostControl"></param>/// <returns></returns>public bool Pause(HostControl hostControl){try{this.scheduler.PauseAll();Console.WriteLine("服务已暂停...");return true;}catch (Exception ex){Console.WriteLine("服务暂停失败:" + ex.Message);return false;}}/// <summary>/// 服务停止/// </summary>/// <param name="hostControl"></param>/// <returns></returns>public bool Stop(HostControl hostControl){try{this.scheduler.Shutdown(false);Console.WriteLine("服务已停止...");return true;}catch (Exception ex){Console.WriteLine("服务停止失败:" + ex.Message);return false;}}}
}

3、完善程序入口
修改启动项目(即控制台项目)的Program.cs,代码如下:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Topshelf;
using Topshelf.HostConfigurators;namespace BTSDataService
{class Program{static void Main(string[] args){Action<HostConfigurator> d = new Action<HostConfigurator>(ActionMethod);HostFactory.Run(d);}}public static void ActionMethod(HostConfigurator hc){hc.Service<ServiceRunner>();hc.SetDescription("我的服务描述");   //windows服务描述hc.SetDisplayName("MyServiceDisplayName");   //windows服务显示的名称hc.SetServiceName("MyServiceName");   //windows服务的名称hc.EnablePauseAndContinue();}
}

任务调度的配置文件

在启动项目(控制台项目)下增加2个配置文件,并把[复制到输出目录]属性设置为"如果较新则复制"。
1、第一个配置文件为quartz.config,内容如下:

# You can configure your scheduler in either <quartz> configuration section
# or in quartz properties file
# Configuration section has precedencequartz.scheduler.instanceName = QuartzTest# configure thread pool info
quartz.threadPool.type = Quartz.Simpl.SimpleThreadPool, Quartz
quartz.threadPool.threadCount = 2
quartz.threadPool.threadPriority = Normal# job initialization plugin handles our xml reading, without it defaults are used
quartz.plugin.xml.type = Quartz.Plugin.Xml.XMLSchedulingDataProcessorPlugin, Quartz
quartz.plugin.xml.fileNames = ~/quartz_jobs.xml# export this server to remoting context
#quartz.scheduler.exporter.type = Quartz.Simpl.RemotingSchedulerExporter, Quartz
#quartz.scheduler.exporter.port = 555
#quartz.scheduler.exporter.bindName = QuartzScheduler
#quartz.scheduler.exporter.channelType = tcp
#quartz.scheduler.exporter.channelName = httpQuartz

你可以通过修改quartz.threadPool.threadCount = 2中的2改变处理定时任务的线程数。
2、第2个配置文件为quartz_jobs.xml,内容如下:

<?xml version="1.0" encoding="UTF-8"?><!-- This file contains job definitions in schema version 2.0 format --><job-scheduling-data xmlns="http://quartznet.sourceforge.net/JobSchedulingData" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" version="2.0"><processing-directives><overwrite-existing-data>true</overwrite-existing-data></processing-directives><schedule><!--调度任务配置--><job><name>ServiceMonitorJob</name><group>Monitor</group><description>服务监控</description><job-type>Wongoing.Jobs.ServiceMonitorJob,Wongoing.Jobs</job-type><durable>true</durable><recover>false</recover></job><!--任务触发配置--><trigger><cron><name>ServiceMonitorJob</name><group>Monitor</group><job-name>ServiceMonitorJob</job-name><job-group>Monitor</job-group><start-time>2019-07-01T00:00:00+08:00</start-time><cron-expression>0/3 * * * * ?</cron-expression></cron></trigger></schedule>
</job-scheduling-data>

可以通过修改0/3 * * * * ?改变触发任务的时机,0/3 * * * * ?代表每3秒触发一次。具体表达式的写法请学习cron表达式。

测试

这时就可以启动此控制台程序,就会看到控制台先输出“服务已启动…”,然后每3秒输出一条“服务监控…”,按Ctrol+C停止服务并退出。

服务安装、启动、停止、卸载

以Release方式编译控制台项目,把Release输出目录下的内容复制到一个指定目录,比如d:\myservice下。以管理员方式运行cmd。通过以下命令进行服务的安装、启动、停止、卸载。
1、服务安装

d:\myservice\BTSDataService.exe install

2、服务启动

d:\myservice\BTSDataService.exe start

3、服务停止

d:\myservice\BTSDataService.exe stop

4、服务卸载

d:\myservice\BTSDataService.exe uninstall

服务安装后,就可以在Windows的服务列表中看到此服务,也可以在windows的服务管理面板中对服务进行启动和停止操作,当然也可以设置为开机启动和禁用。

C#使用Topshelf和Quartz开发处理定时任务的Windows服务程序相关推荐

  1. java quartz spring_JavaLib-quartz | 基于Spring Boot Quartz开发的定时任务

    基于Spring Boot Quartz开发的JavaLib-quartz,目的是帮你快速构建定时任务系统,你可以专心编写你的业务逻辑,而不必关注定时任务具体是如何实现的,他的性能如何,有没有异常以及 ...

  2. topshelf和quartz内部分享

    阅读目录: 介绍 基础用法 调试及安装 可选配置 多实例支持及相关资料 quartz.net 上月在公司内部的一次分享,现把PPT及部分交流内容整理成博客. 介绍 topshelf是创建windows ...

  3. 使用Spring整合Quartz轻松完成定时任务

    一.背景 上次我们介绍了如何使用Spring Task进行完成定时任务的编写,这次我们使用Spring整合Quartz的方式来再一次实现定时任务的开发,以下奉上开发步骤及注意事项等. 二.开发环境及必 ...

  4. Spring 3整合Quartz 2实现定时任务--转

    常规整合 http://www.meiriyouke.net/?p=82 最近工作中需要用到定时任务的功能,虽然Spring3也自带了一个轻量级的定时任务实现,但感觉不够灵活,功能也不够强大.在考虑之 ...

  5. Spring 3整合Quartz 2实现定时任务(转)

    http://www.meiriyouke.net/?p=82 最近工作中需要用到定时任务的功能,虽然Spring3也自带了一个轻量级的定时任务实现,但感觉不够灵活,功能也不够强大.在考虑之后,决定整 ...

  6. quarts集群 运维_精讲Elastic-job + Quartz实现企业级定时任务

    掌握分布式集群方式的定时任务框架,可以弥补企业中常用的单点任务的缺点,以更高的性能更好的稳定性处理分布式定时任务服务:本课程带你掌握分布式框架Elastic-Job和Quartz,在以多种方式开发定时 ...

  7. 集群环境下,谁偷走quartz配置的定时任务

    错误现象: 在本地开发环境中,应用服务启动后TRIGGER_STATE直接就变为ERROR 前段时间在项目中,使用quartz配置一个定时任务,定时任务都持久化到oracle数据库中,但是应用服务器启 ...

  8. Quartz定时器与定时任务知识概括

    Quartz定时器与定时任务知识概括 定时任务调度 其他定时器 Quartz简介 Quartz简单入门 Spring和Quartz集成 SSMM和Quartz集成 Quartz集群 Quartz配置 ...

  9. 使用Spring Boot + Quartz 实现分布式定时任务平台

    本文将从项目实战出发来介绍分布式定时任务的实现.在某些应用场景下要求任务必须具备高可用性和可扩展性,单台服务器不能满足业务需求,这时就需要使用Quartz实现分布式定时任务. 一.分布式任务应用场景 ...

最新文章

  1. ubuntu16.04忘了root密码
  2. 再谈fedora下的音乐和视频播放器的安装
  3. 计算机二进制基础列式,计算机基础;十进制数100对应的二进制数、八进制数和十六进制数分别是...
  4. 学fpga(流水灯)
  5. logger.debug的用处
  6. 选择排序算法(C++版)
  7. Mathpix Snip--图片中识别公式
  8. Word Embedding与Word2Vec
  9. 论文简读-BootEA-《Bootstrapping Entity Alignment with Knowledge Graph Embedding》
  10. word文档中标题跳到表格的下方-解决方法
  11. 某云不限速破解详细教程附工具
  12. nginx出现403错误的解决方法(亲测有效)
  13. 九型性格心理测试 (From Ulla Zang荣格的个人性格测验题目)
  14. Opencv2.4.9、VS2010配置及grabcut代码实例
  15. Vue 适配iOS、Android顶部状态栏(沉浸式,混合APP开发)
  16. Windows返回桌面快捷键
  17. 汽车外饰360vr实景展示有哪些应用场景?
  18. 实现图片中文的识别和获取图片上文字的坐标(java实现)
  19. vue项目中引入Luckysheet
  20. 雅可比行列式的实际意义

热门文章

  1. k-均值(k-means)及Matlab实现
  2. 29、Java——吃货联盟订餐系统(对象+XML)
  3. linux系统一般用来干嘛
  4. 《大数据: Hive 介绍与安装》
  5. 喜报 | 40 under 40 杰出人才榜,Stratifyd 创始人兼CEO汪晓宇博士登榜
  6. SparkCore案例练习:统计广告ID
  7. NYOJ628 小媛在努力
  8. Realsense相机疑难问题
  9. pdf怎么压缩又小又清晰?
  10. 国内从事红外热成像的公司