`

Quartz之InterruptableJob

阅读更多
问题1 由于业务需要,停止Quartz中正在执行的任务
Quartz:你的任务类只需要实现InterruptableJob类就可以了
只要实现一个方法:interrupt(),在这个方法中进行标记的改变,在执行中进行这个标记判断
就可实现中断任务了,另外在调度器上调用方法:sched.interrupt(job.getKey());

在查看Quartz文档中已经有说明了,如下:
The interface to be implemented by Jobs that provide a mechanism for having their execution interrupted. It is NOT a requirement for jobs to implement this interface - in fact, for most people, none of their jobs will.

Interrupting a Job is very analogous in concept and challenge to normal interruption of a Thread in Java.

The means of actually interrupting the Job must be implemented within the Job itself (the interrupt() method of this interface is simply a means for the scheduler to inform the Job that a request has been made for it to be interrupted). The mechanism that your jobs use to interrupt themselves might vary between implementations. However the principle idea in any implementation should be to have the body of the job's execute(..) periodically check some flag to see if an interruption has been requested, and if the flag is set, somehow abort the performance of the rest of the job's work. An example of interrupting a job can be found in the java source for the class org.quartz.examples.DumbInterruptableJob. It is legal to use some combination of wait() and notify() synchronization within interrupt() and execute(..) in order to have the interrupt() method block until the execute(..) signals that it has noticed the set flag.

If the Job performs some form of blocking I/O or similar functions, you may want to consider having the Job.execute(..) method store a reference to the calling Thread as a member variable. Then the Implementation of this interfaces interrupt() method can call interrupt() on that Thread. Before attempting this, make sure that you fully understand what java.lang.Thread.interrupt() does and doesn't do. Also make sure that you clear the Job's member reference to the Thread when the execute(..) method exits (preferably in a finally block.

See Example 7 (org.quartz.examples.example7.DumbInterruptableJob) for a simple implementation demonstration

具体代码如下:
DumbInterruptableJob.java
package org.quartz.examples.example7;

import java.text.SimpleDateFormat;
import java.util.Date;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.quartz.InterruptableJob;
import org.quartz.JobExecutionContext;
import org.quartz.JobExecutionException;
import org.quartz.JobKey;
import org.quartz.UnableToInterruptJobException;


/**
 * @author <a href="mailto:bonhamcm@thirdeyeconsulting.com">Chris Bonham</a>
 * @author Bill Kratzer
 */
public class DumbInterruptableJob implements InterruptableJob {
    
    // logging services
    private static Logger _log = LoggerFactory.getLogger(DumbInterruptableJob.class);
    
    // has the job been interrupted?
    private boolean _interrupted = false;

    // job name 
    private JobKey _jobKey = null;
    
    private static int counts = 0;      
    
 
    public DumbInterruptableJob() {
    }


    public void execute(JobExecutionContext context)
        throws JobExecutionException {

        _jobKey = context.getJobDetail().getKey();
        _log.error("任务Key: " + _jobKey + " 执行时间: " + new SimpleDateFormat("yyyy-MM-dd hh:mm:ss").format(new Date()));

        try {
         
            for (int i = 0; i < 4; i++) {
                try {
                    Thread.sleep(1000L);
                } catch (Exception ignore) {
                    ignore.printStackTrace();
                }                
              
                if(_interrupted) {
                    _log.error("被外界因素停止了这个任务key: " + _jobKey + ",当前执行次数: " + counts);
                    return; // could also choose to throw a JobExecutionException 
                             // if that made for sense based on the particular  
                             // job's responsibilities/behaviors
                }
                //执行业务方法
                userManager();
            }
            
        } finally {
            _log.error("任务执行完成key: " + _jobKey + " 执行时间: " + new SimpleDateFormat("yyyy-MM-dd hh:mm:ss").format(new Date()));
        }
    }
    
    private void userManager() {
    	_log.error("正在执行插入数据库的操作,次数: " + (++counts));		
	}

    public void interrupt() throws UnableToInterruptJobException {
        _log.info("外界正在调用调度器停止这个任务key: " + _jobKey);
        _interrupted = true;
    }
}

InterruptExample.java
package org.quartz.examples.example7;

import static org.quartz.JobBuilder.newJob;
import static org.quartz.SimpleScheduleBuilder.simpleSchedule;
import static org.quartz.TriggerBuilder.newTrigger;
import static org.quartz.DateBuilder.*;

import java.util.Date;

import org.quartz.JobDetail;
import org.quartz.Scheduler;
import org.quartz.SchedulerFactory;
import org.quartz.SchedulerMetaData;
import org.quartz.SimpleTrigger;
import org.quartz.impl.StdSchedulerFactory;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;


public class InterruptExample {

    public void run() throws Exception {
        final Logger log = LoggerFactory.getLogger(InterruptExample.class);
     
        SchedulerFactory sf = new StdSchedulerFactory();
        Scheduler sched = sf.getScheduler();
       
        Date startTime = nextGivenSecondDate(null, 15);

        JobDetail job = newJob(DumbInterruptableJob.class)
            .withIdentity("interruptableJob1", "group1")
            .build();
        
        //当前时间15秒后,每间隔5秒执行一次任务
        SimpleTrigger trigger = newTrigger() 
            .withIdentity("trigger1", "group1")
            .startAt(startTime)
            .withSchedule(simpleSchedule()
                    .withIntervalInSeconds(5)
                    .repeatForever())
            .build();

        Date ft = sched.scheduleJob(job, trigger);
        log.error(job.getKey() + " will run at: " + ft + " and repeat: "
                + trigger.getRepeatCount() + " times, every "
                + trigger.getRepeatInterval() / 1000 + " seconds");

        sched.start();
       
        for(int i=0; i < 10; i++) {
            try {
                Thread.sleep(7000L);                
                sched.interrupt(job.getKey());
            } catch (Exception e) {
            }
        }        
     
        sched.shutdown(true);
      
        SchedulerMetaData metaData = sched.getMetaData();
        log.error("Executed " + metaData.getNumberOfJobsExecuted() + " jobs.");

    }

    public static void main(String[] args) throws Exception {

        InterruptExample example = new InterruptExample();
        example.run();
    }
}
分享到:
评论

相关推荐

    quartz-2.3.2-API文档-中文版.zip

    赠送jar包:quartz-2.3.2.jar; 赠送原API文档:quartz-2.3.2-javadoc.jar; 赠送源代码:quartz-2.3.2-sources.jar; 赠送Maven依赖信息文件:quartz-2.3.2.pom; 包含翻译后的API文档:quartz-2.3.2-javadoc-API...

    quartz指南,Quartz 工程

    文件里面包括 1:Quartz开发指南.pdf 2:Quartz从入门到进阶.pdf 3:QuartzBeginnerExample一个附带的工程例子 4:quartz-1.6.1.zip Quartz是OpenSymphony开源组织在Job scheduling领域又一个开源项目,它...

    quartz-1.6.0.jar和quartz-all-1.6.0.jar

    该压缩包内包含两个quartz的jar包, 分别是quartz-1.6.0.jar和quartz-all-1.6.0.jar

    quartz-2.3.0-API文档-中文版.zip

    赠送jar包:quartz-2.3.0.jar; 赠送原API文档:quartz-2.3.0-javadoc.jar; 赠送源代码:quartz-2.3.0-sources.jar; 赠送Maven依赖信息文件:quartz-2.3.0.pom; 包含翻译后的API文档:quartz-2.3.0-javadoc-API...

    quartz-2.2.3版本的quartz初始化sql语句

    quartz-2.2.3版本的quartz初始化sql语句

    quartz简单实例quartz简单实例

    quartz简单实例quartz简单实例quartz简单实例quartz简单实例

    Autofac.Extras.Quartz, Quartz.Net的Autofac集成.zip

    Autofac.Extras.Quartz, Quartz.Net的Autofac集成 Autofac.Extras.Quartz用于 Quartz.Net的Autofac集成包。Autofac.Extras.Quartz 为每个石英作业创建嵌套的litefime作用域。 完成作业执行后释放嵌套作用域。这允许...

    自开发实现Quartz Web管理工具

    网上能找到的Quartz Web管理的资料都是使用的一个国外人写的Quartz WebApp的东东,功能也很全面。但是作为自己的应用其实用不了那么多功能,一般我们只要可以定义一个job,指定一个Cron表达式完成工作即可,附带的...

    quartz quartz-1.8.6 dbTables 建表sql

    quartz quartz-1.8.6 dbTables quartz动态任务调度需要的数据库脚本。

    quartz内部表.sql

    quartz内部表.sql。

    quartz1.5,quartz1.6,quartz1.8

    Quartz1.5,Quartz1.6,Quartz1.8。Quartz是OpenSymphony开源组织在Job scheduling领域又一个开源项目,它可以与J2EE与J2SE应用程序相结合也可以单独使用。Quartz可以用来创建简单或为运行十个,百个,甚至是好几万个...

    postgres-quartz.sql

    postgres quatrz初始化sql脚本文件、pg、quartz、qrtz_开头的表 配置文件需求修改 #org.quartz.jobStore.driverDelegateClass=org.quartz.impl.jdbcjobstore.StdJDBCDelegate org.quartz.jobStore....

    Quartz.NET-2.0

    Quartz.NET框架的核心是调度器。调度器负责管理Quartz.NET应用运行时环境。Quartz不仅仅是线程和线程管理。为确保可伸缩性,Quartz.NET采用了基于多线程的架构。启动时,框架初始化一套worker线程,这套线程被调度器...

    Quartz原理及实例

    Quartz原理及实例,spring4.x+Quartz.2.2.1结合的开发,静态和动态实例

    lucene与quartz例子

    lucene quartz 例子lucene quartz 例子lucene quartz 例子lucene quartz 例子lucene quartz 例子lucene quartz 例子lucene quartz 例子lucene quartz 例子lucene quartz 例子lucene quartz 例子

    关于spring中quartz的配置

    关于spring中quartz的配置

    深入解读Quartz的原理

    深入解读Quartz的原理,定时任务框架是web开发过程中使用很多的框架之一

    Quartz-2.0.2 CSDN下载

    Quartz框架的核心是调度器。调度器负责管理Quartz应用运行时环境。调度器不是靠自己做所有的工作,而是依赖框架内一些非常重要的部件。 Quartz不仅仅是线程和线程管理。为确保可伸缩性,Quartz采用了基于多线程的...

    Quartz之CronExpression详解

    详细介绍CronExpression表达式设定定时任务的规则

    quartz3种调度形式+传参.zip

    quartz自动调度的3种调度形式+传参 1.单纯的quartz调度 2.spring+quartz调度

Global site tag (gtag.js) - Google Analytics