`

spring-Quartz(入门二)

阅读更多
尽可能的用声明式处理软件配置,其次才考虑编程式的方式。在上一篇《Quartz 框架快速入门(一)》中,如果我们要在 Job 启动之后改变它的执行时间和频度,必须去修改源代码重新编译。这种方式只适用于小的例子程序,但是对于一个大且复杂的系统,这就成了一个问题了。因此,假如能以声明式部署 Quart Job 时,并且也是需求允许的情况下,你应该每次都选择这种方式 
·配置 quartz.properties 文件

文件 quartz.properties 定义了 Quartz 应用运行时行为,还包含了许多能控制 Quartz 运转的属性。这个文件应该放在classpath所指的路径下,比如我们这个java工程,就将它和下面将介绍的jobs.xml一起放在项目根目录下就是。如果不清楚就查看.classpath文件,它里面就配置了你的项目的classpath。

我们来看看最基础的 quartz.properties 文件,并讨论其中一些设置。下面是一个修剪版的 quartz.propertis文件

#============================================================================
# Configure Main Scheduler Properties 
#============================================================================
org.quartz.scheduler.instanceName = TestScheduler
org.quartz.scheduler.instanceId = AUTO
#============================================================================
# Configure ThreadPool 
#============================================================================
org.quartz.threadPool.class = org.quartz.simpl.SimpleThreadPool
org.quartz.threadPool.threadCount = 3
org.quartz.threadPool.threadPriority = 5
#============================================================================
# Configure JobStore 
#============================================================================
org.quartz.jobStore.misfireThreshold = 60000
org.quartz.jobStore.class = org.quartz.simpl.RAMJobStore
#============================================================================
# Configure Plugins
#============================================================================
org.quartz.plugin.triggHistory.class = org.quartz.plugins.history.LoggingJobHistoryPlugin
org.quartz.plugin.jobInitializer.class = org.quartz.plugins.xml.JobInitializationPlugin
org.quartz.plugin.jobInitializer.fileNames = jobs.xml
org.quartz.plugin.jobInitializer.overWriteExistingJobs = true
org.quartz.plugin.jobInitializer.failOnFileNotFound = true
org.quartz.plugin.jobInitializer.scanInterval = 10
org.quartz.plugin.jobInitializer.wrapInUserTransaction = false

·调度器属性

第一部分有两行,分别设置调度器的实例名(instanceName) 和实例 ID (instanceId)。属性 org.quartz.scheduler.instanceName 可以是你喜欢的任何字符串。它用来在用到多个调度器区分特定的调度器实例。多个调度器通常用在集群环境中。(Quartz 集群将会在第十一章,“Quartz 集群”中讨论)。现在的话,设置如下的一个字符串就行:org.quartz.scheduler.instanceName = QuartzScheduler
实际上,这也是当你没有该属性配置时的默认值。

调度器的第二个属性是 org.quartz.scheduler.instanceId。和 instaneName 属性一样,instanceId 属性也允许任何字符串。这个值必须是在所有调度器实例中是唯一的,尤其是在一个集群当中。假如你想 Quartz 帮你生成这个值的话,可以设置为 AUTO。如果 Quartz 框架是运行在非集群环境中,那么自动产生的值将会是 NON_CLUSTERED。假如是在集群环境下使用 Quartz,这个值将会是主机名加上当前的日期和时间。大多情况下,设置为 AUTO 即可。
·线程池属性

接下来的部分是设置有关线程必要的属性值,这些线程在 Quartz 中是运行在后台担当重任的。threadCount 属性控制了多少个工作者线程被创建用来处理 Job。原则上是,要处理的 Job 越多,那么需要的工作者线程也就越多。threadCount 的数值至少为 1。Quartz 没有限定你设置工作者线程的最大值,但是在多数机器上设置该值超过100的话就会显得相当不实用了,特别是在你的 Job 执行时间较长的情况下。这项没有默认值,所以你必须为这个属性设定一个值。

threadPriority 属性设置工作者线程的优先级。优先级别高的线程比级别低的线程更优先得到执行。threadPriority 属性的最大值是常量 java.lang.Thread.MAX_PRIORITY,等于10。最小值为常量 java.lang.Thread.MIN_PRIORITY,为1。这个属性的正常值是 Thread.NORM_PRIORITY,为5。大多情况下,把它设置为5,这也是没指定该属性的默认值。

最后一个要设置的线程池属性是 org.quartz.threadPool.class。这个值是一个实现了 org.quartz.spi.ThreadPool 接口的类的全限名称。Quartz 自带的线程池实现类是 org.quartz.smpl.SimpleThreadPool,它能够满足大多数用户的需求。这个线程池实现具备简单的行为,并经很好的测试过。它在调度器的生命周期中提供固定大小的线程池。你能根据需求创建自己的线程池实现,如果你想要一个随需可伸缩的线程池时也许需要这么做。这个属性没有默认值,你必须为其指定值。

·作业存储设置

作业存储部分的设置描述了在调度器实例的生命周期中,Job 和 Trigger 信息是如何被存储的。我们还没有谈论到作业存储和它的目的;因为对当前例子是非必的,所以我们留待以后说明。现在的话,你所要了解的就是我们存储调度器信息在内存中而不是在关系型数据库中就行了。

把调度器信息存储在内存中非常的快也易于配置。当调度器进程一旦被终止,所有的 Job 和 Trigger 的状态就丢失了。要使 Job 存储在内存中需通过设置  org.quartz.jobStrore.class 属性为 org.quartz.simpl.RAMJobStore。假如我们不希望在 JVM 退出之后丢失调度器的状态信息的话,我们可以使用关系型数据库来存储这些信息。这需要另一个作业存储(JobStore) 实现,我们在后面将会讨论到。第五章“Cron Trigger 和其他”和第六章“作业存储和持久化”会提到你需要用到的不同类型的作业存储实现。
·插件配置

在这个简单的 quartz.properties 文件中最后一部分是你要用到的 Quart 插件的配置。插件常常在别的开源框架上使用到,比如 Apache 的 Struts 框架(见 http://struts.apache.org/)。

一个声明式扩框架的方法就是通过新加实现了 org.quartz.spi.SchedulerPlugin 接口的类。SchedulerPlugin  接口中有给调度器调用的三个方法。

要在我们的例子中声明式配置调度器信息,我们会用到一个 Quartz 自带的叫做 org.quartz.plugins.xml.JobInitializationPlugin 的插件。

默认时,这个插件会在 classpath 中搜索名为 quartz_jobs.xml 的文件并从中加载 Job 和 Trigger 信息。在下下面中讨论 quartz_jobs.xml 文件,这是我们所参考的非正式的 Job 定义文件。

·为插件修改 quartz.properties 配置

JobInitializationPlugin 找寻 quartz_jobs.xml 来获得声明的 Job 信息。假如你想改变这个文件名,你需要修改 quartz.properties 来告诉插件去加载那个文件。例如,假如你想要 Quartz 从名为 my_quartz_jobs.xml 的 XML 文件中加载 Job 信息,你不得不为插件指定这一文件

org.quartz.plugin.triggHistory.class = org.quartz.plugins.history.LoggingJobHistoryPlugin
org.quartz.plugin.jobInitializer.class = org.quartz.plugins.xml.JobInitializationPlugin
org.quartz.plugin.jobInitializer.fileNames = jobs.xml
org.quartz.plugin.jobInitializer.overWriteExistingJobs = true
org.quartz.plugin.jobInitializer.failOnFileNotFound = true
org.quartz.plugin.jobInitializer.scanInterval = 10
org.quartz.plugin.jobInitializer.wrapInUserTransaction = false

我们添加了属性 org.quartz.plugin.jobInitializer.fileName 并设置该属性值为我们想要的文件名。这个文件名要对 classloader 可见,也就是说要在 classpath 下。

当 Quartz 启动后读取 quartz.properties 文件,然后初始化插件。它会传递上面配置的所有属性给插件,这时候插件也就得到通知去搜寻不同的文件。

下面就是目录扫描例子的 Job 定义的 XML 文件。正如上一篇所示例子那样,这里我们用的是声明式途径来配置 Job 和 Trigger 信息的

<?xml version='1.0' encoding='utf-8'?>
<quartz xmlns="http://www.opensymphony.com/quartz/JobSchedulingData"
  xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
  xsi:schemaLocation="http://www.opensymphony.com/quartz/JobSchedulingData
  http://www.opensymphony.com/quartz/xml/job_scheduling_data_1_5.xsd"
  version="1.5">  
  <job>     
    <job-detail>     
     <name>ScanDirectory</name>     
     <group>DEFAULT</group>     
     <description>     
          A job that scans a directory for files      
     </description>     
     <job-class>     
            com.vista.quartz.ScanDirectoryJob      
     </job-class>     
     <volatility>false</volatility>     
     <durability>false</durability>     
     <recover>false</recover>     
     <job-data-map allows-transient-data="true">     
         <entry>     
         <key>SCAN_DIR</key>     
         <value>D:\conf1</value>     
       </entry>     
     </job-data-map>     
    </job-detail>     
     
    <trigger>     
     <simple>     
       <name>scanTrigger</name>     
       <group>DEFAULT</group>     
       <job-name>ScanDirectory</job-name>     
       <job-group>DEFAULT</job-group>     
       <start-time>2008-09-03T14:43:00</start-time>     
       <!-- repeat indefinitely every 10 seconds -->     
       <repeat-count>-1</repeat-count>     
       <repeat-interval>10000</repeat-interval>     
     </simple>     
    </trigger>     
  </job>     
</quartz>

在jobs.xml 中 <start-time> 的格式是:

<start-time>2008-09-03T14:43:00</start-time>
其中T隔开日期和时间,默认时区
或者:

<start-time>2008-09-03T14:43:00+08:00</start-time>
其中+08:00 表示东八区

<job> 元素描述了一个要注册到调度器上的 Job,相当于我们在前面章节中使用 scheduleJob() 方法那样。你所看到的<job-detail> 和  <trigger> 这两个元素就是我们在代码中以编程式传递给方法 schedulerJob() 的参数。前面本质上是与这里一样的,只是现在用的是一种较流行声明的方式。<trigger>元素也是非常直观的:它使用前面同样的属性,但更简单的建立一个 SimpleTrigger。因此仅仅是一种不同的(可论证的且更好的)方式做了上一篇代码 中同样的事情。显然,你也可以支持多个 Job。在上一篇代码 中我们编程的方式那么做的,也能用声明的方式来支持


<?xml version='1.0' encoding='utf-8'?>
<quartz xmlns="http://www.opensymphony.com/quartz/JobSchedulingData"
  xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
  xsi:schemaLocation="http://www.opensymphony.com/quartz/JobSchedulingData
  http://www.opensymphony.com/quartz/xml/job_scheduling_data_1_5.xsd"
  version="1.5">  
<job>     
    <job-detail>     
     <name>ScanDirectory1</name>     
     <group>DEFAULT</group>     
     <description>     
           A job that scans a directory for files      
     </description>     
     <job-class>     
            com.vista.quartz.ScanDirectoryJob      
     </job-class>     
     <volatility>false</volatility>     
     <durability>false</durability>     
     <recover>false</recover>     
     
     <job-data-map allows-transient-data="true">     
     <entry>     
       <key>SCAN_DIR</key>     
         <value>D:\dyk\Java\Tomcat\conf</value>     
     </entry>     
    </job-data-map>     
  </job-detail>     
  <trigger>     
    <simple>     
     <name>scanTrigger1</name>     
     <group>DEFAULT</group>     
     <job-name>ScanDirectory1</job-name>     
     <job-group>DEFAULT</job-group>     
     <start-time>2008-09-03T15:00:10</start-time>     
     <!-- repeat indefinitely every 10 seconds -->     
     <repeat-count>-1</repeat-count>     
     <repeat-interval>10000</repeat-interval>     
    </simple>     
  </trigger>     
</job>      
<job>     
  <job-detail>     
    <name>ScanDirectory2</name>     
    <group>DEFAULT</group>     
    <description>     
          A job that scans a directory for files      
    </description>     
    <job-class>     
          com.vista.quartz.ScanDirectoryJob      
    </job-class>     
    <volatility>false</volatility>     
    <durability>false</durability>     
    <recover>false</recover>     
    <job-data-map allows-transient-data="true">     
      <entry>     
       <key>SCAN_DIR</key>     
       <value>D:\dyk\Java\Tomcat\webapps\MyTest\WEB-INF</value>     
     </entry>     
    </job-data-map>     
  </job-detail>     
  <trigger>     
    <simple>     
     <name>scanTrigger2</name>     
     <group>DEFAULT</group>     
     <job-name>ScanDirectory2</job-name>     
     <job-group>DEFAULT</job-group>     
     <start-time>2008-09-03T15:00:20</start-time>     
     <!-- repeat indefinitely every 15 seconds -->     
     <repeat-count>-1</repeat-count>     
     <repeat-interval>15000</repeat-interval>     
    </simple>     
  </trigger>     
</job>  
</quartz>

最后我们来看看原来的代码简化成如何了:

package com.vista.quartz;

import java.util.Date;      

import org.apache.commons.logging.Log;      
import org.apache.commons.logging.LogFactory;      
import org.quartz.JobDetail;
import org.quartz.Scheduler;      
import org.quartz.SchedulerException;      
import org.quartz.Trigger;
import org.quartz.TriggerUtils;
import org.quartz.impl.StdSchedulerFactory;

public class SimpleScheduler
{
    static Log logger = LogFactory.getLog(SimpleScheduler.class);        
    public static void main(String[] args)
    {      
         SimpleScheduler simple = new SimpleScheduler();      
         try
         {      
             // Create a Scheduler and schedule the Job      
             Scheduler scheduler = simple.createScheduler();        
             // Jobs can be scheduled after Scheduler is running      
             scheduler.start();         
             logger.info("Scheduler started at " + new Date());        
        }
        catch (SchedulerException ex)
        {      
             logger.error(ex);      
        }      
    }      
    public Scheduler createScheduler() throws SchedulerException
    {//创建调度器      
        return StdSchedulerFactory.getDefaultScheduler();
    }  
}


分享到:
评论

相关推荐

    quartz和spring-quartz

    在提供的文件中,“quartz的入门.doc”可能是Quartz的基础教程,介绍如何创建和调度Job;“spring的quartz应用.txt”可能包含Spring-Quartz的具体使用示例和注意事项;“spring-quartz-demo”可能是一个完整的示例...

    spring-boot示例项目

    该项目包含helloworld(快速入门)、web(ssh项目快速搭建)、aop(切面编程)、data-redis(redis缓存)、quartz(集群任务实现)、shiro(权限管理)、oauth2(四种认证模式)、shign(接口参数防篡改重放)、encoder(用户...

    spring-boot学习demo.zip_DEMO_SpringBoot_spring boot_spring-boot_sp

    SpringBoot学习Demo是一个针对初学者的入门项目,旨在帮助开发者快速理解并掌握Spring Boot的核心概念和用法。Spring Boot是Spring框架的一个模块,它简化了创建独立的、生产级别的基于Spring的应用程序的过程,通过...

    spring入门经典

    《Spring入门经典》这本书是Java开发者入门Spring Framework的理想选择,它深入浅出地阐述了Spring的核心概念和技术。Spring Framework作为Java开发领域的主流框架,它的应用广泛且功能强大,旨在简化企业级应用程序...

    quartz实例,quartz入门例子

    在这个Quartz入门例子中,可能包含了一个名为`QuarzTest`的类或配置文件,它是实际运行的入口。通过分析和运行这个例子,你可以了解到如何在Spring中配置和使用Quartz,以及如何创建和调度Job。 学习Quartz时,你...

    spring-boot-demo实例.rar

    Spring Boot 的快速入门通常从创建一个 Maven 或 Gradle 项目开始,引入 `spring-boot-starter-web` 依赖,这将包含 Spring Web MVC 和 Tomcat 服务器。在 `main` 方法中使用 `SpringApplication.run` 启动应用,就...

    quartz入门例子,spring集成配置使用

    Spring集成quartz跑定时任务实例 自己写的例子并为实现job 有测试的主函数,请参考...springCon.quartz文件夹下 为对上诉博客理解透彻 结合spring看其配置的相关信息 就可以明白。

    spring-boot-study-master.zip

    《Spring Boot深度学习指南——基于"spring-boot-study-master.zip"》 ..."spring-boot-study-master.zip"提供了丰富的示例,是学习Spring Boot的宝贵资源,无论是新手入门还是进阶提升,都能从中受益匪浅。

    Java分布式Elastic-Job和Quartz定时任务课程(1.6G)

    1_什么事定时任务.mp4 2_为什么学习定时任务.mp4 3_定时任务技术发展趋势.mp4 4_主流定时任务框架优缺点和什么是分布式定时任务.mp4 5_环境搭建总体流程.mp4 6_前期准备-JDK.mp4 ...24_Spring_Boot整合Simp

    spring整合quartz

    让我们深入探讨这个入门案例,了解如何在Spring应用中设置和使用Quartz。 首先,创建一个Maven工程是必要的,因为Maven是Java开发的标准构建工具,它可以帮助我们管理项目依赖。在`pom.xml`文件中,你需要添加...

    spring-boot-helloworld.zip

    在 "spring-boot-helloworld.zip" 这个压缩包中,我们很可能是找到了一篇关于 Spring Boot 入门的博客文章示例代码,用于展示如何构建一个简单的 "Hello World" 应用。 在 Spring Boot 中创建一个 "Hello World" ...

    quartz案例,包括spring配置设置调度器和入门手册

    3. **Quartz入门** - **创建Job类**:你需要创建一个实现了`org.quartz.Job`接口的类,这个类定义了具体要执行的任务。 - **定义Trigger**:你可以选择不同的`Trigger`类型,如SimpleTrigger或CronTrigger,来决定...

    Quartz入门学习(真丶入门)

    二、Quartz入门 1. **创建作业**:首先,你需要创建一个实现了`org.quartz.Job`接口的类,这个类就是你的任务逻辑。在`execute()`方法中编写实际的业务代码。 2. **定义触发器**:接着,定义一个触发器,设置执行...

    quartz-2.1.6.zip

    "quartz-2.1.6.zip"这个压缩包包含了使用Quartz在Spring中构建定时任务所需的各种组件和文档。 QUICK-START.html 是Quartz的快速入门指南,它通常会提供关于如何安装、配置和启动Quartz的基本步骤,以及如何创建和...

    Spring Boot 教程、技术栈示例代码,快速简单上手教程。

    它集成了大量常用的第三方库配置,如 JDBC、MongoDB、RabbitMQ、Quartz 等,使得开发者可以“零配置”地启动项目,极大地提高了开发效率。 **1. Spring Boot 的核心特性** - **自动配置**:Spring Boot 通过扫描...

    Spring Boot-RESTfull API入门.rar

    它集成了大量常用的第三方库配置,如 JDBC、MongoDB、JPA、RabbitMQ、Quartz 等,使得开发者能够快速地创建生产级别的基于 Spring 的独立应用程序。 RESTful API(Representational State Transfer)是一种软件架构...

    spring-quickstart:Spring Boot 快速入门项目

    标题“spring-quickstart:Spring Boot 快速入门项目”表明这是一个帮助开发者快速了解并上手 Spring Boot 的教程或示例项目。这通常包含一系列的代码样例和指导,旨在解释如何创建、配置和运行一个基本的 Spring ...

    springboot的简单入门

    SpringBoot是Spring框架的一个模块,旨在简化Spring应用的初始搭建以及开发过程。它集成了大量常用的第三方...通过这个入门实践,开发者可以快速了解Spring Boot的工作方式,并为进一步的学习和复杂应用开发打下基础。

    spring boot入门demo

    它集成了大量的常用第三方库配置,如 JDBC、MongoDB、JPA、RabbitMQ、Quartz 等,使得开发者可以快速地创建一个独立运行的、生产级别的基于 Spring 的应用。 在“Spring Boot 入门 Demo”中,我们将探讨以下几个...

    Elastic-job入门教程

    Elastic-job是一个分布式作业调度框架,由当当网开源,它基于quartz二次开发,用于处理大规模分布式任务调度需求。Elastic-job拥有分布式协调、任务分片、弹性扩容和容错等功能,支持在分布式环境下对定时任务进行...

Global site tag (gtag.js) - Google Analytics