简体   繁体   English

如何在不重启服务器的情况下添加带有触发器的作业来运行Quartz.NET调度程序实例?

[英]How to add job with trigger for running Quartz.NET scheduler instance without restarting server?

是否可以添加带有触发器的作业来运行Quartz.NET调度程序实例而无需重新启动服务器?

A fairly robust implementation with ADOJobStore is to have a custom table to store jobs and create a class that inherits from ISchedulerPlugin and IJob to create schedules for your job automatically. 使用ADOJobStore的一个相当强大的实现是拥有一个自定义表来存储作业,并创建一个继承自ISchedulerPlugin和IJob的类,以自动为您的作业创建计划。

Your config will look like this: 您的配置如下所示:

<add key="quartz.plugin.sqlquartzjobs.type" value="(JobSchedulerPlugin assembly path)" />
<add key="quartz.plugin.sqlquartzjobs.RescanCronExpression" value="0 0/5 * * * ?" /> //plugin should fire every five minutes
<add key="quartz.plugin.sqlquartzjobs.ConnectionString" value="(your connection string)" />

Your plugin/job class can look like this: 你的插件/工作类看起来像这样:

public class JobSchedulerPlugin : ISchedulerPlugin, IJob
{
        //Entry point for plugin, quartz server runs when it starts
        public void Initialize(string pluginName, IScheduler sched)
        {
            Name = pluginName;
            Scheduler = sched;
        }

        //Runs after Initialize()
        public void Start()
        {
                //schedule plugin as a job
            JobDataMap jobData = new JobDataMap();
            jobData["ConnectionString"] = ConnectionString;

            IJobDetail job = JobBuilder.Create(this.GetType())
                .WithDescription("Job to rescan jobs from SQL db")
                .WithIdentity(new JobKey(JobInitializationPluginJobName, JobInitializationPluginGroup))
                .UsingJobData(jobData)
                .Build();

             TriggerKey triggerKey = new TriggerKey(JobInitializationPluginJobTriggerName, JobInitializationPluginGroup);

             ITrigger trigger = TriggerBuilder.Create()
                 .WithCronSchedule(ConfigFileCronExpression)
                 .StartNow()
                 .WithDescription("trigger for sql job loader")
                 .WithIdentity(triggerKey)
                 .WithPriority(1)
                 .Build();

             Scheduler.ScheduleJob(job, trigger);
        }
}

Now JobSchedulerPlugin has entered a trigger into QRTZ_TRIGGERS that will fire every five minutes with highest priority. 现在,JobSchedulerPlugin已经进入QRTZ_TRIGGERS的触发器,该触发器将以最高优先级每五分钟触发一次。 You can use it to load jobs from your custom table (let's call it QUARTZJOBS). 您可以使用它从自定义表中加载作业(我们称之为QUARTZJOBS)。 QUARTZJOBS can contain information such as jobnames, assembly paths, dates, status, etc, anything that can be used to help you create triggers efficiently. QUARTZJOBS可以包含诸如工作名,装配路径,日期,状态等信息,以及可用于帮助您有效创建触发器的任何信息。 It should also contain the cron expression to the job. 它还应该包含作业的cron表达式。 This is what you can do when the trigger fires: 这是触发器触发时可以执行的操作:

//Entry point of every job
public void Execute(IJobExecutionContext context)
{
    Scheduler = context.Scheduler;

    JobCollection jobs = LoadJobs(context.JobDetail.JobDataMap["ConnectionString"].ToString());
    JobsWithTriggers jobTriggers = CreateTriggers(jobs);
    SchedulerJob(jobTriggers);
}

//You can use ADO.NET or an ORM here to load job information from the the table
//and push it into a class. 
protected JobCollection LoadJobs(string connectionString);

//In this class you can create JobDetails and ITriggers for each job
//and push them into a custom class
protected JobsWithTriggers CreateTriggers(jobs);

//Finally here you can schedule the jobs
protected void ScheduleJobs(jobstriggers)

In each of the classes above you can add custom validation for making sure triggers are handled appropriately if status or cron expression changes. 在上面的每个类中,您可以添加自定义验证,以确保在状态或cron表达式更改时正确处理触发器。

With this solution the server will never need to be restarted. 使用此解决方案,永远不需要重新启动服务器。 The plugin/job class will scan the table and act accordingly. 插件/作业类将扫描表并相应地执行操作。

What is your data store? 你的数据存储是什么?

Here is one scenario... a little off the beaten path: 这是一个场景......有点偏僻的道路:

You can write a small console app (or similar) that is the "Job Populater". 您可以编写一个小型控制台应用程序(或类似的),即“Job Populater”。

You can wire it to pull job definitions from an xml file, and push them into ADO datastore (sql server). 您可以将其连接到从xml文件中提取作业定义,并将它们推送到ADO数据存储区(sql server)。

Here is my quartz config to do this: 这是我的石英配置来做到这一点:

<quartz>

    <!-- 
    This configuration is a way to have jobs defined in xml, but will get them written to the database.
    See https://stackoverflow.com/questions/21589964/ramjobstore-quartz-jobs-xml-to-adojobstore-data-move/ 
    -->


    <add key="quartz.plugin.xml.type" value="Quartz.Plugin.Xml.XMLSchedulingDataProcessorPlugin, Quartz" />
    <add key="quartz.plugin.xml.fileNames" value="~/Quartz_Jobs_001.xml" />
    <!-- 
    <add key="quartz.plugin.xml.ScanInterval" value="10" />
    -->

    <add key="quartz.jobStore.type" value="Quartz.Impl.AdoJobStore.JobStoreTX, Quartz" />
    <add key="quartz.jobStore.driverDelegateType" value="Quartz.Impl.AdoJobStore.SqlServerDelegate, Quartz"/>
    <add key="quartz.jobStore.dataSource" value="default"/>
    <add key="quartz.dataSource.default.connectionString" value="Server=MyServer\MyInstance;Database=QuartzDB;Trusted_Connection=True;Application Name='quartz_config';"/>
    <add key="quartz.dataSource.default.provider" value="SqlServer-20"/>

</quartz>

Which (as you see in the comments in the xml), I got help with. 哪个(正如你在xml的评论中看到的那样),我得到了帮助。

Here is the original : RAMJobStore (quartz_jobs.xml) to AdoJobStore Data Move 这是原始的: RAMJobStore(quartz_jobs.xml)到AdoJobStore Data Move

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

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