您好,登錄后才能下訂單哦!
怎么理解Quartz 中的JobStore接口,很多新手對此不是很清楚,為了幫助大家解決這個難題,下面小編將為大家詳細講解,有這方面需求的人可以來學習下,希望你能有所收獲。
org.quartz.spi.JobStore 是任務存儲的頂層接口類
org.quartz.simpl.RAMJobStore 是內存存儲機制實現類
org.quartz.impl.jdbcjobstore.JobStoreSupport 是基于JDBC數據庫存儲的抽象類
org.quartz.impl.jdbcjobstore.JobStoreCMT 是受應用容器管理事物的數據庫存儲實現類
org.quartz.impl.jdbcjobstore.JobStoreTX 是不受應用容器事物管理的數據庫存儲實現類
org.quartz.jobStore.class = 上面提到的具體實現類
在quzrtz.properties 中配置以上代碼來告訴quartz我們使用何種存儲機制
內存存儲機制 org.quartz.simpl.RAMJobStore 使用內存存儲的優點是任務的存儲和讀取的速度極快,和數據庫持久化相比差別還是非常大的,而且框架搭建簡單,開箱即用。它的缺點是當Quartz程序或應用程序停止了,伴隨在內存中的數據也會被回收,任務等數據就永久丟失了。
數據庫存儲機制 org.quartz.impl.jdbcjobstore.JobStoreTX TX就是事物的意思,此存儲機制用于Quartz獨立于應用容器的事物管理,如果是Tomcat容器管理的數據源,那我們定義的事物也不會傳播給Quartz框架內部。通俗的講就是不管我們的Service服務本身業務代碼是否執行成功,只要代碼中調用了Quartz API的數據庫操作,那任務狀態就永久持久化了,就算業務代碼拋出運行時異常任務狀態也不會回滾到之前的狀態。 org.quartz.impl.jdbcjobstore.JobStoreCMT CMT的全稱是Container Managed Transactions,表示容器管理事物,也就是讓應用容器托管事物。這里假設應用容器是Tomcat,并且項目和Quartz都是使用Tomcat配置的數據源,那么項目和Quartz的代碼中就可以共用同一個事物,不管是業務代碼還是Quartz內部拋出異常,Service服務內的所有數據操作都會回滾到原始狀態。JobStoreCMT和JobStoreTX最大的區別是JobStoreCMT需要配置兩個數據源,一個是受應用容器管理的數據源,還有一個是不受應用容器管理的數據源。 這里需要想一想為什么需要兩個數據源? 我個人的理解是不受應用容器管理的數據源用來由Quartz內部進行"增刪改查",假如一個觸發器已失效,那么Quartz框架內部就會自動刪除這個觸發器并提交事物,而無需開發人員的項目代碼來處理,全由Quartz內部管理。
什么情況下使用RAMJobStore內存存儲方式呢?
??根據開發中的使用經驗,發現有些任務是隨著項目啟動而啟動的,就算項目關閉或系統宕機,那也沒關系,因為項目重新啟動后此任務又會隨之啟動。如果項目中只存在這類任務,那么就可以用內存存儲。隨著項目啟動有幾種常用的實現方式,第一種是通過實現ServletContextListener監聽器接口,然后在接口實現類的contextInitialized()方法中編寫啟動Job的硬編碼;第二種是通過Quartz的XML配置文件啟動任務。
什么情況下使用JobStoreTX數據庫存儲方式呢?
?使用這種方式需要注意的是,如果在一個業務代碼中需要創建一個Job,那么請把創建Job的代碼編寫在服務代碼的最后面,確保業務代碼運行成功并且沒有拋異常再去啟動Job,如果啟動Job失敗的時候請拋出一個運行時異常使業務代碼進行回滾。
例子:
@Transactional public void demoService(TaskStore taskStore) { // 先執行插入業務操作 taskStoreService.insert(taskStore); // 再執行更新業務操作 taskDetailService.update(taskDetail); // 最后啟動定時任務 QuartzUtils.addJob("testName", DemoJob.class, "0 * * * * * ?"); }
注意例子中的addJob()方法中捕獲了異常后進行重新封裝再拋出運行時異常的,目的是Quartz內部錯誤時確保業務代碼回滾。
什么情況下使用JobStoreCMT數據庫存儲方式呢?
??JobStoreCMT和JobStoreTX的區別前文已經介紹了,在實際開發的過程中我還沒有在項目中使用過此種方式。一般情況下都是使用的JobStoreTX。如果大家的項目中有著嚴格的事物管理,那么建議使用JobStoreCMT存儲方式。
@Component public class JobFactory extends AdaptableJobFactory { @Autowired private AutowireCapableBeanFactory capableBeanFactory; @Override protected Object createJobInstance(final TriggerFiredBundle bundle) throws Exception { // 調用父類的方法 Object jobInstance = super.createJobInstance(bundle); // 進行注入 capableBeanFactory.autowireBean(jobInstance); return jobInstance; } } 這個類的作用就是講Job的實例化交給IOC去進行。 其實問題在于: Job對象的實例化過程是在Quartz中進行的,注入的實體類是在Spring容器當中的 所以在job中無法注入Srping容器的實體類。 解決方案:將Job Bean也納入到Spring容器的管理之中,Spring容器自然能夠為Job Bean自動裝配好所需的依賴。 如何納入:Job的創建都是通過JobFactory創建的。 官網解釋為證: 翻譯:JobFactory負責生成Job類的實例。 JobFactory 有2個實現類:AdaptableJobFactory 和 SimpleJobFactory。 自定義的工廠類 JobFactory 繼承 AdaptableJobFactory 。 通過調用父類 AdaptableJobFactory 的方法createJobInstance來實現對Job的實例化。 在Job實例化完以后,再調用自身方法為創建好的Job實例進行屬性自動裝配并將其納入到Spring容器的管理之中。(通過AutowireCapableBeanFactory納入)。
看完上述內容是否對您有幫助呢?如果還想對相關知識有進一步的了解或閱讀更多相關文章,請關注億速云行業資訊頻道,感謝您對億速云的支持。
免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。