Java EE Server 上寫一個排程工作,只要加一個 @Schedule 就可以了,Tomcat 除了用 Java SE 的 TimerTask 來排程外的另一個選擇就是 quartz,看了一下有支援 Thread Pool,設定檔不用寫在程式碼上,之後要寫 ant 來置換比較方便,就決定用 quartz。
使用版本
Tomcat7 + quartz 2.1.7
步驟
http://www.quartz-scheduler.org/documentation/quartz-2.1.x/quick-start 是一個官網的簡單使用說明,下面是我自己使用的筆記。
1) 安裝
到
官網下載,解壓縮後 lib 下的 jar 檔都加入專案的 build path。
2) 啟用 quartz
web.xml 加入 QuartzInitializerListener,QuartzInitializerListener 實作了 javax.servlet.ServletContextListener,QuartzInitializerListener 在 Web App 啟動後就會初始化 quartz 相關的設定。
WebContent/WEB-INF/web.xml
3) 設定 quartz
WebContent/WEB-INF/classes/quartz.properties
4) 設定排程工作
quartz_data.xml 內,
- 建立一個 Job,取名並指定實作類別。
- 建立一個 Trigger,取名,指定 Job 和執行時間。
關於 Trigger 的執行時間設定可參考:
http://www.quartz-scheduler.org/documentation/quartz-2.x/tutorials/crontrigger
WebContent/WEB-INF/classes/quartz_data.xml
5) 實作排程工作
FooJob.java
public class FooJob implements Job
{
@Override
public void execute(final JobExecutionContext ctx) throws JobExecutionException
{
// To something here!
}
}
問題
1) 執行時發生 java.lang.NoClassDefFoundError: javax/transaction/UserTransaction
嚴重: Exception sending context initialized event to listener instance of class org.quartz.ee.servlet.QuartzInitializerListener
java.lang.NoClassDefFoundError: javax/transaction/UserTransaction
下載 jta-1.1.jar 後,加入專案的 build path。
2) Tomcat7 關閉 Web App 出現 memory leak 警告。
[DefaultQuartzScheduler_Worker-5] but has failed to stop it. This is very likely to create a memory leak
這是因為 Tomcat7 關閉 Web App 時,沒有正確關閉 quartz 的關係,在QuartzInitializerListener 加入下列初始參數。
WebContent/WEB-INF/web.xml
參考