Bootstrap

Grails Quartz插件 定时调度任务

Quartz插件可以使Grails应用程序按照指定的时间间隔或cron表达式来执行调度任务。Grails系统通过spring配置使用Quartz Enterprise Job Scheduler 实现,但是编码时按照规约可以很容易的实现。

Grails-Quartz 0.4.1是当前稳定版本。Grails-Quartz 0.4.2是最新正在开发的版本。(已经发布了)

 

1 插件安装

在应用文件夹路径下键入以下命令

grails install-plugin quartz

如果以上命令由于某种原因不行,试一下下面这个

grails install-plugin http://cloud.github.com/downloads/nebolsin/grails-quartz/grails-quartz-0.4.1.zip

 

2  用法

调度任务(Scheduling Jobs)


在命令行键入“grails create-job”命令并输入任务名称,Grails会创建一个新的任务,并把它放到"grails-app/jobs"路径下。

class MyJob {
  static triggers = {
    simple name: 'mySimpleTrigger', startDelay: 60000, repeatInterval: 1000 
  }

  def group = "MyGroup"

  def execute(){
    print "Job run!"
  }
}

 

上述例子会等待1分钟后每秒调用execute方法一次。'repeatInterval' 和'startDelay'属性的单位是毫秒,值必须是int或long。如果这两个属性不指定,则使用默认值(repeatInterval为1分钟,startDelay为30秒)

 

jobs默认情况下在test环境不运行。

 

调度Cron任务(Scheduling a Cron Job)


可以使用cron表达式调度任务。

class MyJob  {
  static triggers = {
    cron name: 'myTrigger', cronExpression: "0 0 6 * * ?"
  }
def group = "MyGroup"
def execute(){ print "Job run!" }

 }

 

组合触发器任务


可以使用组合触发器调度任务。

class MyJob {
    static
 triggers = {
        simple name:'simpleTrigger', startDelay:10000, repeatInterval: 30000, repeatCount: 10
        cron name:'cronTrigger', startDelay:10000, cronExpression: '0/6 * 15 * * ?'
        custom name:'customTrigger', triggerClass:MyTriggerClass, myParam:myValue, myAnotherParam:myAnotherValue
    }

def execute() { println "Job run!" } }

上面这个例子中,scheduler(调度器)启动10秒后,job会每隔30秒执行一次,一共执行11次(simpleTrigger);在15点时每6秒执行一次(15:00:00, 15:00:06, 15:00:12, … — 这个由'cronTrigger'配置的),自定义的触发器触发时执行。

 

三种触发器可以支持的参数如下

  • simple :
    • name — 触发器的名称标识
    • startDelay — 调度器启动与第一次执行任务之间的间隔 (单位:毫秒)
    • repeatInterval — 连续两次执行任务之间的时间间隔(单位:毫秒)
    • repeatCount — 任务执行(1 + repeatCount)  次之后停止 (=0 执行一次 或=-1 执行无限次)
  • cron :
    • name — 触发器的名称标识
    • startDelay — 调度器启动与第一次执行任务之间的间隔 (单位:毫秒)
    • cronExpression — cron表达式
  • custom :
    • triggerClass — 自定义的实现了Trigger接口的类
    • 自定义触发器的需要的其他参数

动态任务调度(Dynamic Jobs Scheduling)


从0.4.1版本开始,可以使用动态调度任务。

可以使用以下方法:

  • MyJob.schedule(String cronExpression, Map params?) — 创建cron触发器;
  • MyJob.schedule(Long repeatInterval, Integer repeatCount?, Map params?) — 创建simple触发器: 间隔repeatInterval毫秒重复job repeatCount+1次;
  • MyJob.schedule(Date scheduleDate, Map params?) — 在指定日期调度执行一个任务;
  • MyJob.schedule(Trigger trigger) — 使用自定义触发器调度任务执行;
  • MyJob.triggerNow(Map params?) — 强制任务立刻执行.

每个方法都带有一个可选的‘params’参数。可以用它传递数据。

class MyJob { 

def execute(context) {
println context.mergedJobDataMap.get('foo')
}

}

// 在controller (或 service, 或其他地方):

MyJob.triggerNow([foo:"It Works!" ])

 

依赖注入和jobs(Dependency Injection and Jobs)


Jobs被配置为按名称自动绑定(auto-wiring by name),属性可以注入到jobs里。为获取data source可以声明

def dataSource

或者一个Service类

def myService

Grails application context 配置为使用规约,因此大部分类型可以使用属性名称很简单地注入(即大多数情况下首字母小写)。

使用JobExecutionContext(Using JobExecutionContext)

从0.3.2开始,你可以定义在job中这样定义execute方法def execute(context){} ,这由Quartz's JobExecutionContext 提供。

如通过 context.getMergedJobDataMap() 提供一些参数给job一样,你可以从context中获取某些信息(触发器名称,上次执行时间

,下次执行时间等)。如果你的job是有状态的(看下面的并发一节),JobExecutionContext中的job数据在每次执行job时也会持久化。


配置插件(Configuring the plugin)


从0.3版本开始,插件支持配置文件,配置内容保存在grails-app/conf/QuartzConfig.groovy文件中。语法与默认的Grails配置文件 Config.groovy 相同

在命令行键入'grails install-quartz-config',可以获得一个初始的 Quartz配置文件。文件内容大致如下:
quartz {
autoStartup = true
jdbcStore = false
}

environments {

    test {

            quartz {

                     autoStartup = false

                       }

            }

}

目前支持的选项:
  • autoStartup — 应用启动时,自动启动Quartz调度器 (默认值: true )
  • jdbcStore — 如果需要Quartz持久化 jobs到DB时设置为true(默认值: false ), 还需要提供quartz.properties 文件,确信所需的数据表在db中存在 (see Clustering section below for the sample config and automatic tables creation using Hibernate)
还可以创建
grails-app/conf/quartz.properties文件来为
Quartz调度器提供不同的选项
(参考 Quartz configuration reference

 ).

 

日志(Logging)


log被自动注入到你的job类里,但没有激活它。在 grails-app/conf/Config.groovy中配置如下语句即可设置log级别。

debug 'grails.app.task'

 

Hibernate会话和任务(Hibernate Sessions and Jobs)


默认配置每次job执行时绑定一个Hibernate会话。当你要open session或者domain类持久化操作时这是必须的。

如果你不使用,可以使用 'sessionRequired' 属性重载这个行为。

def sessionRequired = false

 

配置并发执行(Configuring concurrent execution)


默认Jobs可以并发执行,因此即使前一个同样的任务正在执行,一个新的任务也可以创建并执行。如果想重载这种行为,可以使用'concurrent' 属性

def concurrent = false

;