苏联解体心得:quartz 在WEB中应用小结 - My english is poor,but I am happy to speak my poor english! - JavaEye技术网站

来源:百度文库 编辑:九乡新闻网 时间:2024/07/14 00:49:48

quartz 在WEB中应用小结

文章分类:Java编程前一个项目曾经用到过quartz,没好好总结一下,现在的项目中又用到了,害得我又花了查了两天查资料、做测试!现在OK了,系统目前运行正常,做个小结。

1. 基本配置

官网上有quartz的所有版本,下一个,把quartz-all-*.jar(根据需要)添加到lib目录中,在classpath目录添加quartz.properties属性文件,接下来你就可以进行开发了。
这是quartz.properties的基本配置。
Java代码
  1. #============================================================================  
  2. # Configure Main Scheduler Properties    
  3. #============================================================================  
  4.   
  5. org.quartz.scheduler.instanceName = TestScheduler  
  6. org.quartz.scheduler.instanceId = AUTO  
  7.   
  8. #============================================================================  
  9. # Configure ThreadPool    
  10. #============================================================================  
  11.   
  12. org.quartz.threadPool.class = org.quartz.simpl.SimpleThreadPool  
  13. org.quartz.threadPool.threadCount = 3  
  14. org.quartz.threadPool.threadPriority = 5  
  15.   
  16. #============================================================================  
  17. # Configure JobStore    
  18. #============================================================================  
  19.   
  20. org.quartz.jobStore.misfireThreshold = 60000  
  21.   
  22. org.quartz.jobStore.class = org.quartz.simpl.RAMJobStore  


2. web基本应用

quartz在web项目中有多种应用方式,和项目使用的其他技术也有关系。

添加一个servlet,将它配置到web.xml中:

Java代码
  1.   
  2.         QuartzStartupServlet  
  3.         com.StartupServlet  
  4.         1  
  5.   


这样你就可以在这个servlet中,在服务器加载的时候同时加载定时任务:

Java代码
  1. public void init(ServletConfig cfg) throws javax.servlet.ServletException  
  2.     {  
  3.         log.info("server start!");  
  4.         initScheduler(cfg);  
  5.     }  
  6.   
  7.     protected void initScheduler(ServletConfig cfg)  
  8.     {  
  9.         try  
  10.         {  
  11.             SchedulerFactory sf = new StdSchedulerFactory();  
  12.             Scheduler scheduler = sf.getScheduler();  
  13.             SimpleExample simpleExample = new SimpleExample(scheduler);  
  14.             simpleExample.run();  
  15.         } catch (Exception e)  
  16.         {  
  17.             log.error(e);  
  18.         }  
  19.     }  


任务定义和加载在quartz的示例中有,这里不多费口舌了。

3. xml形式的任务配置

xml形式的应用,需要使用quartz的xml支持插件,只需有实现Job接口的任务就可以;这时需要在web.xml中添加默认的servlet配置:

Java代码
  1.   
  2.         Quartz Initializer Servlet  
  3.         QuartzInitializer  
  4.           
  5.             org.quartz.ee.servlet.QuartzInitializerServlet  
  6.           
  7.         1  
  8.       


在quartz.properties中添加xml配置需要的参数:

Java代码
  1. #============================================================================  
  2. # Configure Plugins   
  3. #============================================================================  
  4.   
  5. org.quartz.plugin.triggHistory.class = org.quartz.plugins.history.LoggingJobHistoryPlugin  
  6.   
  7. org.quartz.plugin.jobInitializer.class = org.quartz.plugins.xml.JobInitializationPlugin  
  8. org.quartz.plugin.jobInitializer.fileNames = jobs.xml  
  9. org.quartz.plugin.jobInitializer.overWriteExistingJobs = true  
  10. org.quartz.plugin.jobInitializer.failOnFileNotFound = true  
  11. org.quartz.plugin.jobInitializer.scanInterval = 10  
  12. org.quartz.plugin.jobInitializer.wrapInUserTransaction = false  

上面配置中的fileNames是指向的classpath根目录。

在xml文件中定义任务名称和触发器,例如:Java代码
  1.   
  2.   
  3.       
  4.           
  5.             dailybalance  
  6.             balance  
  7.             com.SimpleJob  
  8.           
  9.           
  10.               
  11.                 dailybalancetrigger  
  12.                 balance  
  13.                 dailybalance  
  14.                 balance  
  15.                 0/50 * * * * ?  
  16.               
  17.           
  18.       
  19.   

这样就OK了!几种配置可以同时应用,不会冲突!

4. quartz的动态时间管理

有时需要在不停止web服务的情况下修改任务的执行时间格式,网上的资料大多是在使用spring框架支持时如何动态管理时间格式的介绍。在使用spring支持时可以,不使用spring时更加简单。

动态时间管理的关键是要共享调度管理器对象Scheduler,我们可以在最初加载任务调度的时候将它添加到servlet上下文中。
Java代码
  1. SchedulerFactory sf = new StdSchedulerFactory();  
  2. Scheduler scheduler = sf.getScheduler();  
  3. ......  
  4. ......  
  5. cfg.getServletContext().setAttribute(SCHEDULER_KEY, scheduler);  
  6. scheduler.start();  

这样,我们就可以在需要修改时间格式的地方使用了!下面的ctt变量就是一个ServletContext对象。通过Scheduler的getTrigger方法取到触发器,用触发器对象的getCronExpression方法可以获得时间格式。之后你可以另外创建一个同名的触发器,也可以修改现有触发器,再让调度管理器重新加载到内存就可以了!
Java代码
  1. /** 
  2.      * reset quartz job time 
  3.      */  
  4.     public void reSetLotteryLoseBiddingTime(int lotteryType, Date date)  
  5.     {  
  6.         scheduler = (Scheduler) this.ctt.getAttribute(TIMING_WORK_SCHEDULER);  
  7.         try  
  8.         {  
  9.             String lotteryName = "";  
  10.             switch (lotteryType)  
  11.             {  
  12.             case 1://  
  13.                 lotteryName = "ssq";  
  14.                 break;  
  15.             case 2://   
  16.             {  
  17.                 lotteryName = "3D";  
  18.             }  
  19.                 break;  
  20.             case 3://   
  21.             {  
  22.                 lotteryName = "qlc";  
  23.             }  
  24.                 break;  
  25.             case 4://   
  26.             {  
  27.                 lotteryName = "23x5";  
  28.             }  
  29.                 break;  
  30.             default:  
  31.                 break;  
  32.             }  
  33.   
  34.             loseBiddingJob = scheduler.getJobDetail("loseBiddingJob_" + lotteryName, "loseBiddingGroup");  
  35.             loseBiddingTrigger = (CronTrigger) scheduler.getTrigger("loseBiddingTrigger_" + lotteryName,  
  36.                     "loseBiddingGroup");  
  37.             String time = loseBiddingTrigger.getCronExpression();  
  38.             if (!time.equals(this.timeFormat(date)))  
  39.             {  
  40.                 loseBiddingTrigger = new CronTrigger("loseBiddingTrigger_" + lotteryName, "loseBiddingGroup",  
  41.                         "loseBiddingJob_" + lotteryName, "loseBiddingGroup", this.timeFormat(date));  
  42.                 Date ft = scheduler.rescheduleJob("loseBiddingTrigger_" + lotteryName, "loseBiddingGroup",  
  43.                         loseBiddingTrigger);  
  44.                 log.info(loseBiddingJob.getFullName() + " has been scheduled to run at: " + ft  
  45.                         + " and excute based on expression: " + loseBiddingTrigger.getCronExpression());  
  46.             }  
  47.         } catch (Exception e)  
  48.         {  
  49.             log.error(e);  
  50.         }  
  51.     }  



5.相关问题

配置完成后,定时任务不加载执行,在日志中报错:
java.lang.NoSuchMethodError:org.apache.commons.collections.SetUtils.orderedSet(Ljava/util/Set;)Ljava/util/Set;
这个是commons-collections.jar版本过低的原因,更换个新版本的就可以了!

还有,为了防止开发人员在本地测试时,执行定时任务造成数据冲突,需要对主机服务器Ip进行判断,只有指定的服务器上才可以执行定时任务!
Java代码
  1. public boolean compareService(String thisIp)  
  2. {  
  3.     Properties properties = this.getProperties();  
  4.     String serviceIp = "";  
  5.     try  
  6.     {  
  7.         if (properties != null)  
  8.         {  
  9.             serviceIp = properties.getProperty("timing.work.serviceIp");  
  10.             if (serviceIp != null && serviceIp.equals(thisIp))  
  11.                 return true;  
  12.         }  
  13.     } catch (Exception e)  
  14.     {  
  15.         log.error(e);  
  16.     }  
  17.     return false;  
  18. }  




quartz还可以对数据库操作,还有JobStore等等,以后应用到再说!哈!附带一份《quartz开发指南》!