Bevezetés a kvarcba

1. Áttekintés

Kvarc egy nyílt forráskódú munkaütemezési keretrendszer, amely teljes egészében Java nyelven íródott, és mindkettőhöz használható J2SE és J2EE alkalmazások. Nagy rugalmasságot kínál az egyszerűség feláldozása nélkül.

Bármely feladat végrehajtásához összetett ütemezéseket hozhat létre. Ilyenek pl. naponta, minden második pénteken 19: 30-kor futó feladatok vagy csak minden hónap utolsó napján.

Ebben a cikkben megnézzük azokat az elemeket, amelyekkel a Quartz API-val létrehozhatunk egy munkát. A tavasszal kombinációban történő bevezetéshez javasoljuk a Tavaszi ütemezés kvarc használatával lehetőséget.

2. Maven-függőségek

A következő függőséget kell hozzáadnunk a pom.xml:

 org.quartz-ütemező kvarc 2.3.0 

A legújabb verzió megtalálható a Maven Central adattárban.

3. A Quartz API

A keret lényege a Ütemező. Felelős az alkalmazásunk futási környezetének kezeléséért.

A méretezhetőség biztosítása érdekében a Quartz többszálas architektúrára épül. Amikor elindult, a keretrendszer inicializálja a dolgozói szálak készletét amelyeket a Ütemező végrehajtani Állások.

A keretrendszer így futtatható sok Állások egyidejűleg. Ez egy lazán összekapcsolt készletre is támaszkodik ThreadPool felügyeleti komponensek a szálkörnyezet kezeléséhez.

Az API legfontosabb interfészei:

  • Ütemező - az elsődleges API a keretrendszer ütemezőjével való interakcióhoz
  • Állás - egy olyan interfész, amelyet az általunk végrehajtani kívánt összetevők valósítanak meg
  • JobDetail - a példányok definiálására szolgál Munkas
  • Trigger - egy komponens, amely meghatározza az adott ütemtervet Munka előadják
  • JobBuilder - építeni szokott JobDetail példányok, amelyek meghatározzák a Állások
  • TriggerBuilder - építeni szokott Trigger példányok

Vessünk egy pillantást ezekre az összetevőkre.

4. Ütemező

Mielőtt használhatnánk a Ütemező, azt példányosítani kell. Ehhez felhasználhatjuk a gyárat SchedulerFactory:

SchedulerFactory schedulerFactory = new StdSchedulerFactory (); Ütemező ütemező = SchululerFactory.getScheduler ();

A ÜtemezőÉletciklusát a létrehozása határolja, a SchedulerFactory és felhívást annak Leállitás() módszer. Miután létrehozta a Ütemező interfész használható hozzáadáshoz, eltávolításhoz és listázáshoz Állások és Kiváltók, és hajtson végre más ütemezéssel kapcsolatos műveleteket (például szüneteltetheti a ravaszt).

Azonban, a Ütemező nem fog reagálni egyetlen kiváltó tényezőre sem, amíg azt a Rajt() módszer:

ütemező.start ();

5. Állások

A Munka olyan osztály, amely végrehajtja a Munka felület. Csak egy egyszerű módszere van:

public class SimpleJob megvalósítja a Job {public void execute (JobExecutionContext arg0) dobja a JobExecutionException {System.out.println ("Ez egy kvarcfeladat!"); }}

Amikor az Jobé kiváltó tüzek, a végrehajtani () metódust az ütemező egyik munkaszála hívja meg.

A JobExecutionContext Az ennek a metódusnak átadott objektum biztosítja a jobpéldány számára a futási környezetre vonatkozó információkat, és kezelési lehetőséget a Ütemező amely kivégezte, fogantyú a Trigger ami kiváltotta a végrehajtást, a munkát JobDetail objektumot és néhány más elemet.

A JobDetail objektumot a Quartz kliens hozza létre a Munka hozzáadódik a Ütemező. Lényegében a munkapéldány meghatározása:

JobDetail job = JobBuilder.newJob (SimpleJob.class) .Identity ("myJob", "group1") .build ();

Ez az objektum különféle tulajdonságbeállításokat is tartalmazhat a Munka, valamint a JobDataMap, amellyel állami információk tárolhatók munkakörünk adott példányához.

5.1. JobDataMap

A JobDataMap bármely olyan adatobjektum tárolására szolgál, amelyet elérhetővé kívánunk tenni a jobpéldány számára, amikor végrehajtja. JobDataMap a Java megvalósítása Térkép interfészt, és néhány hozzáadott kényelmi módszerrel rendelkezik a primitív típusú adatok tárolásához és visszakereséséhez.

Íme egy példa adatok beillesztésére a JobDataMap építése közben JobDetail, mielőtt hozzáadná a munkát az ütemezőhöz:

JobDetail job = newJob (SimpleJob.class) .withIdentity ("myJob", "group1") .usingJobData ("jobSays", "Hello World!") .UsingJobData ("myFloatValue", 3.141f) .build ();

És itt van egy példa arra, hogyan férhet hozzá ezekhez az adatokhoz a munka végrehajtása során:

public class SimpleJob megvalósítja a Job {public void execute (JobExecutionContext context) dobja a JobExecutionException {JobDataMap dataMap = context.getJobDetail (). getJobDataMap (); String jobSays = dataMap.getString ("jobSays"); float myFloatValue = dataMap.getFloat ("myFloatValue"); System.out.println ("Job azt mondja:" + jobSays + ", és val:" + myFloatValue); }}

A fenti példa a következőt írja: „Job azt mondja, hogy Hello World !, és a val értéke 3,141”.

Setter metódusokat is felvehetünk az osztályunkba, amelyek megfelelnek a JobDataMap.

Ha ezt tesszük, akkor a Quartz alapértelmezett JobFactory a megvalósítás automatikusan felhívja ezeket a beállókat, amikor a feladat példányos, így megakadályozva annak szükségességét, hogy az értékeket kifejezetten lekerítsük a térképről a végrehajtási módszerünkön belül.

6. Kiváltók

Trigger objektumokat használnak a végrehajtás kiváltására Állások.

Amikor be akarjuk ütemezni a Munka, be kell állítanunk egy triggeret és módosítanunk kell annak tulajdonságait az ütemezési követelmények konfigurálásához:

Trigger trigger = TriggerBuilder.newTrigger () .withIdentity ("myTrigger", "group1") .startNow () .withSchedule (SimpleScheduleBuilder.simpleSchedule () .withIntervalInSeconds (40) .repeatbuild (());

A Trigger lehet egy JobDataMap társul hozzá. Ez hasznos a paraméterek továbbításához az a-hoz Munka amelyek specifikusak a ravaszt kivégzéseire.

Különböző típusú triggerek vannak a különböző ütemezési igényekhez. Mindegyiknek más és más TriggerKey tulajdonságok identitásuk nyomon követésére. Néhány más tulajdonság azonban közös az összes trigger típusnál:

  • A jobKey tulajdonság a munka azonosságát jelzi, amelyet végre kell hajtani, amikor az indító elindul.
  • A kezdési idő tulajdonság azt jelzi, hogy az eseményindító ütemezése mikor lép életbe először. Az érték a java.util.Dátum objektum, amely meghatároz egy adott pillanatot egy adott naptári dátumhoz. Bizonyos ravasztípusoknál a ravasz a megadott kezdési időpontban indul. Mások számára egyszerűen azt az időpontot jelöli, amikor a menetrendnek meg kell kezdődnie.
  • A idő vége tulajdonság jelzi, hogy mikor kell törölni az eseményindító ütemezését.

A kvarc maroknyi különféle kiváltó kivitelű, de a leggyakrabban használtak SimpleTrigger és CronTrigger.

6.1. Kiemelten fontos

Néha, amikor sok kiváltó tényezőnk van, a kvarc nem biztos, hogy elegendő erőforrással rendelkezik az összes tervezett munka egyszerre történő elindításához. Ebben az esetben érdemes ellenőriznünk, hogy kiváltóink közül melyik válik elérhetővé először. Pontosan ez az kiemelten fontos egy ravaszon lévő tulajdonság használható.

Például, ha tíz indítót egyszerre indítanak és csupán négy munkaszál áll rendelkezésre, akkor a legmagasabb prioritású első négy indítót hajtják végre először. Ha nem állítunk be prioritást egy triggerre, akkor az alapértelmezett ötöt használ. Bármely egész érték megengedett prioritásként, pozitív vagy negatív.

Az alábbi példában két különböző prioritású kiváltó tényezőnk van. Ha nincs elegendő erőforrás az összes indító egyszerre történő elindításához, triggerA elsőként kirúgják:

Trigger triggerA = TriggerBuilder.newTrigger () .withIdentity ("triggerA", "group1") .startNow () .withPriority (15) .withSchedule (SimpleScheduleBuilder.simpleSchedule () .withIntervalInSeconds (40). ; Trigger triggerB = TriggerBuilder.newTrigger () .withIdentity ("triggerB", "group1") .startNow () .withPriority (10) .withSchedule (SimpleScheduleBuilder.simpleSchedule () .withIntervalInSeconds (20). ;

6.2. Gyújtáselhárítási utasítások

Gyújtáskimaradás akkor fordul elő, ha tartósan kivált hiányzik tüzelési ideje a Ütemező vagy ha nincsenek elérhető szálak a Quartz szálkészletében.

A különböző trigger típusokhoz különböző gyújtáskimaradás-utasítások állnak rendelkezésre. Alapértelmezés szerint intelligens házirend-utasítást használnak. Amikor az ütemező elindul, megkeresi azokat az állandó triggereket, amelyek hibásan működtek. Ezt követően mindegyiket frissíti az egyedileg konfigurált gyújtáskimaradás-utasítások alapján.

Vessünk egy pillantást az alábbi példákra:

Trigger misFiredTriggerA = TriggerBuilder.newTrigger () .startAt (DateUtils.addSeconds (new Date (), -10)) .build (); Trigger misFiredTriggerB = TriggerBuilder.newTrigger () .startAt (DateUtils.addSeconds (new Date (), -10)) .withSchedule (SimpleScheduleBuilder.simpleSchedule () .withMisfireHandlingInstructionFbuNow ().

A ravaszt 10 másodperccel ezelőtt futtattuk (tehát 10 másodperccel késik a létrehozás időpontja) a gyújtáskimaradás szimulálására, pl. mert az ütemező leállt, vagy nem állt rendelkezésre elegendő mennyiségű munkásszál. Természetesen valós helyzetben soha nem ütemeznénk be az ilyen kiváltó tényezőket.

Az első ravaszt (misFiredTriggerA) nincsenek gyújtáselhárítási utasítások. Ezért hívott okos politika abban az esetben használatos, és a következőnek hívják: withMisfireHandlingInstructionFireNow (). Ez azt jelenti, hogy a feladat azonnal végrehajtásra kerül, miután az ütemező felfedezte a gyújtáskimaradást.

A második kiváltó ok kifejezetten meghatározza, hogy milyen viselkedésre számítunk, ha hibás gyújtás történik. Ebben a példában véletlenül ugyanaz az intelligens politika.

6.3. SimpleTrigger

SimpleTrigger olyan forgatókönyvek esetén használatos, amikor egy munkát egy adott időpontban kell végrehajtanunk. Ez történhet pontosan egyszer, vagy meghatározott időközönként ismételten.

Példaként említhetjük, ha 2018. január 13-án pontosan 12: 20: 00-kor elbocsátunk egy munkát. Hasonlóképpen, akkor elkezdhetjük ebben az időben, majd további öt alkalommal, tíz másodpercenként.

Az alábbi kódban a dátum myStartTime Korábban definiálták, és egy adott időbélyeg kiváltójának létrehozására szolgál:

SimpleTrigger trigger = (SimpleTrigger) TriggerBuilder.newTrigger () .withIdentity ("trigger1", "group1") .startAt (myStartTime) .forJob ("job1", "group1") .build ();

Ezután hozzunk létre egy ravaszt egy adott pillanatra, majd tíz másodpercenként ismételjük meg tízszer:

SimpleTrigger trigger = (SimpleTrigger) TriggerBuilder.newTrigger () .withIdentity ("trigger2", "group1") .startAt (myStartTime) .withSchedule (simpleSchedule () .withIntervalInSeconds (10) .withRepeatCount (10). ) .épít();

6.4. CronTrigger

A CronTrigger akkor használatos, ha naptárszerű nyilatkozatokon alapuló ütemezésekre van szükségünk. Például meghatározhatjuk az égetési ütemezéseket, mint pl minden pénteken délben vagy minden hétköznap 9: 30-kor.

A Cron-Expressions segítségével konfigurálhatjuk a példányokat CronTrigger. Ezek a kifejezések a következőkből állnak: Húrok amelyek hét részkifejezésből állnak. A Cron-Expressions-ról itt olvashatunk többet.

Az alábbi példában létrehozunk egy ravaszt, amely minden második percben minden reggel 8 és 17 óra között lő:

CronTrigger trigger = TriggerBuilder.newTrigger () .withIdentity ("trigger3", "group1") .withSchedule (CronScheduleBuilder.cronSchedule ("0 0/2 8-17 * *?")) .ForJob ("myJob", "group1" ) .épít();

7. Következtetés

Ebben a cikkben bemutattuk a Ütemező kiváltani a Munka. Láttunk néhányat a leggyakrabban használt kiváltó opciók közül is: SimpleTrigger és CronTrigger.

A kvarc segítségével egyszerű vagy összetett ütemtervek készíthetők több tucat, száz vagy még több feladat végrehajtására. További információ a keretrendszerről a fő weboldalon található.

A példák forráskódja megtalálható a GitHub oldalon.