### QuartzTest.java - Obtain, start, and shutdown scheduler Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/quick-start.html This example shows the basic lifecycle of a Quartz scheduler: get the default scheduler, start it, and shut it down. Note that the application will not terminate until shutdown() is called because active threads exist. ```java import org.quartz.Scheduler; import org.quartz.SchedulerException; import org.quartz.impl.StdSchedulerFactory; import static org.quartz.JobBuilder.*; import static org.quartz.TriggerBuilder.*; import static org.quartz.SimpleScheduleBuilder.*; public class QuartzTest { public static void main(String[] args) { try { // Grab the Scheduler instance from the Factory Scheduler scheduler = StdSchedulerFactory.getDefaultScheduler(); // and start it off scheduler.start(); scheduler.shutdown(); } catch (SchedulerException se) { se.printStackTrace(); } } } ``` -------------------------------- ### Instantiate and start scheduler, schedule job with trigger Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/tutorials/tutorial-lesson-01.html Creates a StdSchedulerFactory, gets a Scheduler, starts it, defines a JobDetail for HelloJob, creates a Trigger that fires now and every 40 seconds, and schedules the job. Note that the scheduler must be started before triggers fire. ```java SchedulerFactory schedFact = new org.quartz.impl.StdSchedulerFactory(); Scheduler sched = schedFact.getScheduler(); sched.start(); // define the job and tie it to our HelloJob class JobDetail job = newJob(HelloJob.class) .withIdentity("myJob", "group1") .build(); // Trigger the job to run now, and then every 40 seconds Trigger trigger = newTrigger() .withIdentity("myTrigger", "group1") .startNow() .withSchedule(simpleSchedule() .withIntervalInSeconds(40) .repeatForever()) .build(); // Tell quartz to schedule the job using our trigger sched.scheduleJob(job, trigger); ``` -------------------------------- ### Sample log output from Quartz scheduler startup and shutdown Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/quick-start.html This is the console output when logging is not configured, showing the scheduler creation, initialization, start, and shutdown messages. ```text [INFO] 21 Jan 08:46:27.857 AM main [org.quartz.core.QuartzScheduler] Quartz Scheduler v.2.0.0-SNAPSHOT created. [INFO] 21 Jan 08:46:27.859 AM main [org.quartz.simpl.RAMJobStore] RAMJobStore initialized. [INFO] 21 Jan 08:46:27.865 AM main [org.quartz.core.QuartzScheduler] Scheduler meta-data: Quartz Scheduler (v2.0.0) 'Scheduler' with instanceId 'NON_CLUSTERED' Scheduler class: 'org.quartz.core.QuartzScheduler' - running locally. NOT STARTED. Currently in standby mode. Number of jobs executed: 0 Using thread pool 'org.quartz.simpl.SimpleThreadPool' - with 50 threads. Using job-store 'org.quartz.simpl.RAMJobStore' - which does not support persistence. and is not clustered. [INFO] 21 Jan 08:46:27.865 AM main [org.quartz.impl.StdSchedulerFactory] Quartz scheduler 'Scheduler' initialized from default resource file in Quartz package: 'quartz.properties' [INFO] 21 Jan 08:46:27.866 AM main [org.quartz.impl.StdSchedulerFactory] Quartz scheduler version: 2.0.0 [INFO] 21 Jan 08:46:27.866 AM main [org.quartz.core.QuartzScheduler] Scheduler Scheduler_$_NON_CLUSTERED started. [INFO] 21 Jan 08:46:27.866 AM main [org.quartz.core.QuartzScheduler] Scheduler Scheduler_$_NON_CLUSTERED shutting down. [INFO] 21 Jan 08:46:27.866 AM main [org.quartz.core.QuartzScheduler] Scheduler Scheduler_$_NON_CLUSTERED paused. [INFO] 21 Jan 08:46:27.867 AM main [org.quartz.core.QuartzScheduler] Scheduler Scheduler_$_NON_CLUSTERED shutdown complete. ``` -------------------------------- ### Start the scheduler Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/examples/Example1.html Starts the scheduler so it can begin firing triggers. ```java sched.start(); ``` -------------------------------- ### HelloJob implementation Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/tutorials/tutorial-lesson-03.html Example job class implementing the Job interface. It must have a no-argument constructor and its execute method is called by the scheduler. ```java public class HelloJob implements Job { public HelloJob() { } public void execute(JobExecutionContext context) throws JobExecutionException { System.err.println("Hello! HelloJob is executing."); } } ``` -------------------------------- ### Example of a Quartz-defined DataSource with HikariCP Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/configuration/ConfigDataSources.html Shows the properties for a Quartz-created DataSource using HikariCP. Note that the provider property must be set to 'hikaricp' to select HikariCP over c3p0. The example uses an Oracle JDBC driver and includes a connection test query. ```properties org.quartz.dataSource.myDS.driver = hikaricp org.quartz.dataSource.myDS.driver = oracle.jdbc.driver.OracleDriver org.quartz.dataSource.myDS.URL = jdbc:oracle:thin:@10.0.1.23:1521:demodb org.quartz.dataSource.myDS.user = myUser org.quartz.dataSource.myDS.password = myPassword org.quartz.dataSource.myDS.maximumPoolSize = 30 org.quartz.dataSource.myDS.connectionTestQuery = SELECT 1 org.quartz.dataSource.myDS.idleTimeout = 0 ``` -------------------------------- ### Example of Using a Custom ConnectionProvider Implementation Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/configuration/ConfigDataSources.html Shows how to configure a custom ConnectionProvider class. After instantiating the class, Quartz can automatically set configuration properties on the instance, bean-style. ```properties org.quartz.dataSource.myCustomDS.connectionProvider.class = com.foo.FooConnectionProvider org.quartz.dataSource.myCustomDS.someStringProperty = someValue org.quartz.dataSource.myCustomDS.someIntProperty = 5 ``` -------------------------------- ### Example of a Quartz-defined DataSource (with c3p0 default provider) Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/configuration/ConfigDataSources.html Shows a complete quartz.properties configuration for a DataSource named 'myDS' using the c3p0 provider, including driver, URL, user, password, and maxConnections. ```properties org.quartz.dataSource.myDS.driver = oracle.jdbc.driver.OracleDriver org.quartz.dataSource.myDS.URL = jdbc:oracle:thin:@10.0.1.23:1521:demodb org.quartz.dataSource.myDS.user = myUser org.quartz.dataSource.myDS.password = myPassword org.quartz.dataSource.myDS.maxConnections = 30 ``` -------------------------------- ### Instantiating the Default Scheduler Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/cookbook/CreateScheduler.html Creates a Scheduler using the default configuration from 'quartz.properties' in the working directory, classpath, or the fall-back default in quartz.jar. The scheduler will not execute jobs until start() is called. ```java // the 'default' scheduler is defined in "quartz.properties" found // in the current working directory, in the classpath, or // resorts to a fall-back default that is in the quartz.jar SchedulerFactory sf = new StdSchedulerFactory(); Scheduler scheduler = sf.getScheduler(); // Scheduler will not execute jobs until it has been started (though they can be scheduled before start()) scheduler.start(); ``` -------------------------------- ### CronTrigger Example 1 - fires every 5 minutes Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/tutorials/tutorial-lesson-06.html Cron expression that fires every 5 minutes. ```cron 0 0/5 * * * ? ``` -------------------------------- ### Calendar Example with HolidayCalendar and addCalendar Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/tutorials/tutorial-lesson-04.html Shows how to instantiate HolidayCalendar, add excluded dates, register it with the scheduler via addCalendar, and create two triggers that use the calendar via modifiedByCalendar to skip holidays. ```java HolidayCalendar cal = new HolidayCalendar(); cal.addExcludedDate( someDate ); cal.addExcludedDate( someOtherDate ); sched.addCalendar("myHolidays", cal, false); Trigger t = newTrigger() .withIdentity("myTrigger") .forJob("myJob") .withSchedule(dailyAtHourAndMinute(9, 30)) // execute job daily at 9:30 .modifiedByCalendar("myHolidays") // but not on holidays .build(); // .. schedule job with trigger Trigger t2 = newTrigger() .withIdentity("myTrigger2") .forJob("myJob2") .withSchedule(dailyAtHourAndMinute(11, 30)) // execute job daily at 11:30 .modifiedByCalendar("myHolidays") // but not on holidays .build(); // .. schedule job with trigger2 ``` -------------------------------- ### Example of a Datasource referenced from an Application Server Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/configuration/ConfigDataSources.html Shows the properties for referencing a DataSource managed by an application server via JNDI. The jndiURL property is required, and the other properties are optional for connecting to the JNDI context. ```properties org.quartz.dataSource.myOtherDS.jndiURL=jdbc/myDataSource org.quartz.dataSource.myOtherDS.java.naming.factory.initial=com.evermind.server.rmi.RMIInitialContextFactory org.quartz.dataSource.myOtherDS.java.naming.provider.url=ormi://localhost org.quartz.dataSource.myOtherDS.java.naming.security.principal=admin org.quartz.dataSource.myOtherDS.java.naming.security.credentials=123 ``` -------------------------------- ### Building a SimpleTrigger with Misfire Handling Instruction Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/tutorials/tutorial-lesson-05.html Shows how to build a SimpleTrigger with a misfire instruction using SimpleScheduleBuilder. The example sets a 5-minute interval, repeats forever, and uses withMisfireHandlingInstructionNextWithExistingCount(). ```java trigger = newTrigger() .withIdentity("trigger7", "group1") .withSchedule(simpleSchedule() .withIntervalInMinutes(5) .repeatForever() .withMisfireHandlingInstructionNextWithExistingCount()) .build(); ``` -------------------------------- ### Instantiating a Specific Scheduler From a Specific Property File Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/cookbook/CreateScheduler.html Initializes a StdSchedulerFactory with a properties file name (fileName) before obtaining the Scheduler. The scheduler will not execute jobs until start() is called. ```java StdSchedulerFactory sf = new StdSchedulerFactory(); sf.initialize(fileName); Scheduler scheduler = sf.getScheduler(); // Scheduler will not execute jobs until it has been started (though they can be scheduled before start()) scheduler.start(); ``` -------------------------------- ### Accessing JobDataMap from JobExecutionContext Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/tutorials/tutorial-lesson-03.html This example shows how to retrieve data from the merged JobDataMap during job execution. It demonstrates getting a string, a float, and an ArrayList from the map, and then modifying the ArrayList. ```java public class DumbJob implements Job { public DumbJob() { } public void execute(JobExecutionContext context) throws JobExecutionException { JobKey key = context.getJobDetail().getKey(); JobDataMap dataMap = context.getMergedJobDataMap(); // Note the difference from the previous example String jobSays = dataMap.getString("jobSays"); float myFloatValue = dataMap.getFloat("myFloatValue"); ArrayList state = (ArrayList)dataMap.get("myStateData"); state.add(new Date()); System.err.println("Instance " + key + " of DumbJob says: " + jobSays + ", and val is: " + myFloatValue); } } ``` -------------------------------- ### Define job and trigger, and schedule job Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/quick-start.html This example shows how to define a job tied to a class, create a trigger that runs now and repeats every 40 seconds, and schedule the job with the trigger. You need to allow time for the job to execute before calling shutdown(), e.g., Thread.sleep(60000). ```java // define the job and tie it to our HelloJob class JobDetail job = newJob(HelloJob.class) .withIdentity("job1", "group1") .build(); // Trigger the job to run now, and then repeat every 40 seconds Trigger trigger = newTrigger() .withIdentity("trigger1", "group1") .startNow() .withSchedule(simpleSchedule() .withIntervalInSeconds(40) .repeatForever()) .build(); // Tell quartz to schedule the job using our trigger scheduler.scheduleJob(job, trigger); ``` -------------------------------- ### Instantiating a Specific Scheduler From Specific Properties Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/cookbook/CreateScheduler.html Initializes a StdSchedulerFactory with a Properties object (schedulerProperties) before obtaining the Scheduler. The scheduler will not execute jobs until start() is called. ```java StdSchedulerFactory sf = new StdSchedulerFactory(); sf.initialize(schedulerProperties); Scheduler scheduler = sf.getScheduler(); // Scheduler will not execute jobs until it has been started (though they can be scheduled before start()) scheduler.start(); ``` -------------------------------- ### Setting Properties on a Custom ThreadPool Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/configuration/ConfigThreadPool.html Example configuration for a custom thread pool implementation. Properties are set reflectively by naming them with the prefix 'org.quartz.threadPool.' followed by the property name. ```properties org.quartz.threadPool.class = com.mycompany.goo.FooThreadPool org.quartz.threadPool.somePropOfFooThreadPool = someValue ``` -------------------------------- ### Getting data from JobDataMap during job execution Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/tutorials/tutorial-lesson-03.html Example DumbJob that retrieves JobKey and JobDataMap from the execution context, then reads primitive values using getString and getFloat. ```java public class DumbJob implements Job { public DumbJob() { } public void execute(JobExecutionContext context) throws JobExecutionException { JobKey key = context.getJobDetail().getKey(); JobDataMap dataMap = context.getJobDetail().getJobDataMap(); String jobSays = dataMap.getString("jobSays"); float myFloatValue = dataMap.getFloat("myFloatValue"); System.err.println("Instance " + key + " of DumbJob says: " + jobSays + ", and val is: " + myFloatValue); } } ``` -------------------------------- ### Basic quartz.properties configuration Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/quick-start.html A minimal Quartz configuration file that sets the scheduler name to 'MyScheduler', uses 3 threads in the thread pool, and stores all data in memory using RAMJobStore. This is a good starting point before moving to a database-backed job store. ```java org.quartz.scheduler.instanceName = MyScheduler org.quartz.threadPool.threadCount = 3 org.quartz.jobStore.class = org.quartz.simpl.RAMJobStore ``` -------------------------------- ### Define jobs and triggers in jobs.xml Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/cookbook/JobInitPlugin.html Self-explanatory example of a jobs.xml file that declaratively defines a job and a cron trigger. The job includes a job-data-map with entries, and the trigger fires every night at 4:30 am using the cron expression '0 30 4 * * ?'. ```xml my-very-clever-job MYJOB_GROUP The job description com.acme.scheduler.job.CleverJob burger-type hotdog dressing-list ketchup,mayo my-trigger MYTRIGGER_GROUP my-very-clever-job MYJOB_GROUP 0 30 4 * * ? ``` -------------------------------- ### JobListener Interface Definition Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/tutorials/tutorial-lesson-07.html Defines the org.quartz.JobListener interface with methods for job execution start, veto, and completion events. Implement this interface to receive job-related events. ```java public interface JobListener { public String getName(); public void jobToBeExecuted(JobExecutionContext context); public void jobExecutionVetoed(JobExecutionContext context); public void jobWasExecuted(JobExecutionContext context, JobExecutionException jobException); } ``` -------------------------------- ### Create a SchedulerListener by extending SchedulerListenerSupport Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/cookbook/SchedulerListeners.html Extend SchedulerListenerSupport and override methods for events you're interested in, such as schedulerStarted, schedulerShutdown, and jobScheduled. The example defines a class MyOtherSchedulerListener in package foo. ```java package foo; import org.quartz.Trigger; import org.quartz.listeners.SchedulerListenerSupport; public class MyOtherSchedulerListener extends SchedulerListenerSupport { @Override public void schedulerStarted() { // do something with the event } @Override public void schedulerShutdown() { // do something with the event } @Override public void jobScheduled(Trigger trigger) { // do something with the event } } ``` -------------------------------- ### Create three SimpleTriggers with different priorities Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/examples/Example14.html Creates three triggers that all start 5 seconds from now but have different priorities (1, default 5, and 10) and repeat at different intervals. The priorities act as tie-breakers when triggers compete for the single thread. ```java // Calculate the start time of all triggers as 5 seconds from now Date startTime = futureDate(5, IntervalUnit.SECOND); // First trigger has priority of 1, and will repeat after 5 seconds Trigger trigger1 = newTrigger() .withIdentity("PriorityNeg5Trigger5SecondRepeat") .startAt(startTime) .withSchedule(simpleSchedule().withRepeatCount(1).withIntervalInSeconds(5)) .withPriority(1) .forJob(job) .build(); // Second trigger has default priority of 5 (default), and will repeat after 10 seconds Trigger trigger2 = newTrigger() .withIdentity("Priority5Trigger10SecondRepeat") .startAt(startTime) .withSchedule(simpleSchedule().withRepeatCount(1).withIntervalInSeconds(10)) .forJob(job) .build(); // Third trigger has priority 10, and will repeat after 15 secondsTrigger trigger3 = newTrigger() .withIdentity("Priority10Trigger15SecondRepeat") .startAt(startTime) .withSchedule(simpleSchedule().withRepeatCount(1).withIntervalInSeconds(15)) .withPriority(10) .forJob(job) .build(); ``` -------------------------------- ### CronTrigger Example 2 - fires every 5 minutes at 10 seconds after the minute Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/tutorials/tutorial-lesson-06.html Cron expression that fires every 5 minutes, at 10 seconds after the minute (e.g., 10:00:10 am, 10:05:10 am). ```cron 10 0/5 * * * ? ``` -------------------------------- ### Using Setter Injection with JobDataMap Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/tutorials/tutorial-lesson-03.html This example demonstrates how to use setter methods to receive JobDataMap values. The default JobFactory will automatically call these setters when the job is instantiated, allowing for cleaner execute() code. ```java public class DumbJob implements Job { String jobSays; float myFloatValue; ArrayList state; public DumbJob() { } public void execute(JobExecutionContext context) throws JobExecutionException { JobKey key = context.getJobDetail().getKey(); JobDataMap dataMap = context.getMergedJobDataMap(); // Note the difference from the previous example state.add(new Date()); System.err.println("Instance " + key + " of DumbJob says: " + jobSays + ", and val is: " + myFloatValue); } public void setJobSays(String jobSays) { this.jobSays = jobSays; } public void setMyFloatValue(float myFloatValue) { this.myFloatValue = myFloatValue; } public void setState(ArrayList state) { this.state = state; } } ``` -------------------------------- ### Set connection validation query in quartz.properties Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/faq.html Specify a validation query for a Quartz-managed data source to detect failed connections. The example uses 'select 0 from dual', which is efficient for Oracle; other databases require an appropriate query. ```properties org.quartz.dataSource.myDS.validationQuery=select 0 from dual ``` -------------------------------- ### Schedule a Job with Quartz (Java) Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/cookbook/ScheduleJob.html Use this snippet to schedule a job that fires immediately and does not repeat. It defines a job instance with identity 'job1' in group 'group1', creates a trigger with identity 'trigger1' in group 'group1' that starts now, and schedules the job with the scheduler. Note: the code uses 'job' in the schedule call, but the variable is defined as 'job1'. ```java // Define job instance JobDetail job1 = newJob(ColorJob.class) .withIdentity("job1", "group1") .build(); // Define a Trigger that will fire "now", and not repeat Trigger trigger = newTrigger() .withIdentity("trigger1", "group1") .startNow() .build(); // Schedule the job with the trigger sched.scheduleJob(job, trigger); ``` -------------------------------- ### Build a trigger for a specific moment in time, then repeating every ten seconds ten times Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/tutorials/tutorial-lesson-05.html Creates a trigger that fires at a start time and then repeats every 10 seconds for 10 repeats (total 11 firings). Uses a JobDetail handle for the job. ```java trigger = newTrigger() .withIdentity("trigger3", "group1") .startAt(myTimeToStartFiring) // if a start time is not given (if this line were omitted), "now" is implied .withSchedule(simpleSchedule() .withIntervalInSeconds(10) .withRepeatCount(10)) // note that 10 repeats will give a total of 11 firings .forJob(myJob) // identify job with handle to its JobDetail itself .build(); ``` -------------------------------- ### Using SimpleTrigger with 48-hour interval Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/cookbook/BiDailyTrigger Creates a SimpleTrigger that starts at 3:00 PM tomorrow and repeats every 48 hours. Note that due to daylight saving time shifts, the firing time may not always be 3:00 PM. ```java trigger = newTrigger() .withIdentity("trigger3", "group1") .startAt(tomorrowAt(15, 0, 0) // first fire time 15:00:00 tomorrow .withSchedule(simpleSchedule() .withIntervalInHours(2 * 24) // interval is actually set at 48 hours' worth of milliseconds .repeatForever()) .build(); ``` -------------------------------- ### Schedule Job #2 every other minute at 15 seconds Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/examples/Example3.html Defines a job and a cron trigger with expression "15 0/2 * * * ?" to run every other minute starting at 15 seconds past the minute, then schedules it. ```java job = newJob(SimpleJob.class) .withIdentity("job2", "group1") .build(); trigger = newTrigger() .withIdentity("trigger2", "group1") .withSchedule(cronSchedule("15 0/2 * * * ?")) .build(); sched.scheduleJob(job, trigger); ``` -------------------------------- ### Configure QuartzInitializerServlet in web.xml Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/cookbook/ServletInitScheduler.html Adds a start-up servlet to web.xml to initialize Quartz. Uses an init parameter for shutdown-on-unload and sets load-on-startup to 2. The servlet class is org.quartz.ee.servlet.QuartzInitializerServlet. ```xml ... QuartzInitializer org.quartz.ee.servlet.QuartzInitializerServlet shutdown-on-unload true 2 ... ``` -------------------------------- ### Configure QuartzInitializerListener in web.xml Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/cookbook/ServletInitScheduler.html Adds a context listener to web.xml to initialize Quartz. Uses context parameters for config file path, shutdown-on-unload, wait-on-shutdown, and start-scheduler-on-load. The listener class is org.quartz.ee.servlet.QuartzInitializerListener. ```xml ... quartz:config-file /some/path/my_quartz.properties quartz:shutdown-on-unload true quartz:wait-on-shutdown false quartz:start-scheduler-on-load true ... org.quartz.ee.servlet.QuartzInitializerListener ... ``` -------------------------------- ### Build a trigger for a specific moment in time, with no repeats Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/tutorials/tutorial-lesson-05.html Creates a SimpleTrigger that fires once at a specific start time, identifying the job by name and group strings. ```java SimpleTrigger trigger = (SimpleTrigger) newTrigger() .withIdentity("trigger1", "group1") .startAt(myStartTime) // some Date .forJob("job1", "group1") // identify job with name, group strings .build(); ``` -------------------------------- ### Using CalendarIntervalTrigger with 90-minute interval Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/cookbook/NinetyMinTrigger.html Creates a trigger with identity 'trigger3' in group 'group1', starts immediately, and repeats every 90 minutes using calendarIntervalSchedule(). ```java trigger = newTrigger() .withIdentity("trigger3", "group1") .startNow() .withSchedule(calendarIntervalSchedule() .withIntervalInMinutes(90)) .build(); ``` -------------------------------- ### Create SimpleTrigger for next even minute Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/examples/Example1.html Computes a run time at the next even minute and creates a SimpleTrigger with identity 'trigger1' in group 'group1' that starts at that time. ```java // compute a time that is on the next round minute Date runTime = evenMinuteDate(new Date()); // Trigger the job to run on the next round minute Trigger trigger = newTrigger() .withIdentity("trigger1", "group1") .startAt(runTime) .build(); ``` -------------------------------- ### Define a job and trigger using Quartz builder DSL Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/tutorials/tutorial-lesson-02.html Shows how to create a JobDetail and Trigger using the fluent builder API, then schedule the job with the scheduler. The job is tied to HelloJob.class, named 'myJob' in group 'group1', and the trigger runs now and every 40 seconds. ```java // define the job and tie it to our HelloJob class JobDetail job = newJob(HelloJob.class) .withIdentity("myJob", "group1") // name "myJob", group "group1" .build(); // Trigger the job to run now, and then every 40 seconds Trigger trigger = newTrigger() .withIdentity("myTrigger", "group1") .startNow() .withSchedule(simpleSchedule() .withIntervalInSeconds(40) .repeatForever()) .build(); // Tell quartz to schedule the job using our trigger sched.scheduleJob(job, trigger); ``` -------------------------------- ### Using SimpleTrigger with 90-minute interval Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/cookbook/NinetyMinTrigger.html Creates a trigger with identity 'trigger3' in group 'group1', starts immediately, and repeats every 90 minutes indefinitely using simpleSchedule(). ```java trigger = newTrigger() .withIdentity("trigger3", "group1") .startNow() .withSchedule(simpleSchedule() .withIntervalInMinutes(90) .repeatForever()) .build(); ``` -------------------------------- ### Configure Quartz to use TerracottaJobStore Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/tutorials/tutorial-lesson-09.html Sets the JobStore class to TerracottaJobStore and specifies the Terracotta server URL. This provides scaling and robustness without a database. ```properties org.quartz.jobStore.class = org.terracotta.quartz.TerracottaJobStore org.quartz.jobStore.tcConfigUrl = localhost:9510 ``` -------------------------------- ### General pattern for defining a Quartz plugin Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/configuration/ConfigPlugins.html Shows the general configuration pattern for defining a Quartz plugin. The class must have a no-arg constructor, and properties are set reflectively. Only primitive data type values (including Strings) are supported. ```properties org.quartz.plugin.NAME.class = com.foo.MyPluginClass org.quartz.plugin.NAME.propName = propValue org.quartz.plugin.NAME.prop2Name = prop2Value ``` -------------------------------- ### Sample configuration of JobInitializationPlugin Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/configuration/ConfigPlugins.html Configures the XMLSchedulingDataProcessorPlugin, which reads jobs and triggers from an XML file and adds them to the scheduler during initialization. It can also delete existing data. The fileNames property points to the XML file, and failOnFileNotFound is set to true. ```properties org.quartz.plugin.jobInitializer.class = \ org.quartz.plugins.xml.XMLSchedulingDataProcessorPlugin org.quartz.plugin.jobInitializer.fileNames = \ data/my_job_data.xml org.quartz.plugin.jobInitializer.failOnFileNotFound = true ``` -------------------------------- ### Standby and restart a Quartz scheduler Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/cookbook/SchedulerStandby.html Call scheduler.standby() to pause trigger firing and job execution. Call scheduler.start() to resume. The comment notes that start() was previously invoked on the scheduler. ```java // start() was previously invoked on the scheduler scheduler.standby(); // now the scheduler will not fire triggers / execute jobs // ... scheduler.start(); // now the scheduler will fire triggers and execute jobs ``` -------------------------------- ### HelloJob execute method Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/examples/Example1.html Implements the Job interface's execute method to log a 'Hello World' message with the current date/time. This is the job that runs when the trigger fires. ```java public void execute(JobExecutionContext context) throws JobExecutionException { // Say Hello to the World and display the date/time _log.info("Hello World! - " + new Date()); } ``` -------------------------------- ### Quartz properties for clustered JDBC JobStore Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/configuration/ConfigJDBCJobStoreClustering.html Use this configuration to set up a Quartz scheduler cluster with the JDBC JobStore. It sets the scheduler instance name and ID, configures a SimpleThreadPool with 25 threads, enables clustering with a check-in interval of 20000 ms, and defines an Oracle data source. The job store uses the OracleDelegate and the QRTZ_ table prefix. ```properties #============================================================================ # Configure Main Scheduler Properties #============================================================================ org.quartz.scheduler.instanceName = MyClusteredScheduler org.quartz.scheduler.instanceId = AUTO #============================================================================ # Configure ThreadPool #============================================================================ org.quartz.threadPool.class = org.quartz.simpl.SimpleThreadPool org.quartz.threadPool.threadCount = 25 org.quartz.threadPool.threadPriority = 5 #============================================================================ # Configure JobStore #============================================================================ org.quartz.jobStore.misfireThreshold = 60000 org.quartz.jobStore.class = org.quartz.impl.jdbcjobstore.JobStoreTX org.quartz.jobStore.driverDelegateClass = org.quartz.impl.jdbcjobstore.oracle.OracleDelegate org.quartz.jobStore.useProperties = false org.quartz.jobStore.dataSource = myDS org.quartz.jobStore.tablePrefix = QRTZ_ org.quartz.jobStore.isClustered = true org.quartz.jobStore.clusterCheckinInterval = 20000 #============================================================================ # Configure Datasources #============================================================================ org.quartz.dataSource.myDS.driver = oracle.jdbc.driver.OracleDriver org.quartz.dataSource.myDS.URL = jdbc:oracle:thin:@polarbear:1521:dev org.quartz.dataSource.myDS.user = quartz org.quartz.dataSource.myDS.password = quartz org.quartz.dataSource.myDS.maxConnections = 5 org.quartz.dataSource.myDS.validationQuery=select 0 from dual ``` -------------------------------- ### CronTrigger Example 3 - fires at 10:30, 11:30, 12:30, 13:30 on Wednesdays and Fridays Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/tutorials/tutorial-lesson-06.html Cron expression that fires at 10:30, 11:30, 12:30, and 13:30 on every Wednesday and Friday. ```cron 0 30 10-13 ? * WED,FRI ``` -------------------------------- ### Static Imports for Matchers and Keys Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/tutorials/tutorial-lesson-07.html Static imports for matcher and key classes to make matcher definitions cleaner. Use these imports to simplify the listener registration code. ```java import static org.quartz.JobKey.*; import static org.quartz.impl.matchers.KeyMatcher.*; import static org.quartz.impl.matchers.GroupMatcher.*; import static org.quartz.impl.matchers.AndMatcher.*; import static org.quartz.impl.matchers.OrMatcher.*; import static org.quartz.impl.matchers.EverythingMatcher.*; ...etc. ``` -------------------------------- ### Create SimpleTrigger with 10-second interval Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/cookbook/TenSecTrigger.html Use SimpleTrigger to schedule a trigger that fires every 10 seconds, repeating forever. The trigger is built with identity 'trigger3' in group 'group1' and starts immediately. ```java trigger = newTrigger() .withIdentity("trigger3", "group1") .startNow() .withSchedule(simpleSchedule() .withIntervalInSeconds(10) .repeatForever()) .build(); ``` -------------------------------- ### Using CalendarIntervalTrigger with 2-day interval Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/cookbook/BiDailyTrigger Creates a CalendarIntervalTrigger that starts at 3:00 PM tomorrow and repeats every 2 calendar days, preserving the time of day across daylight saving changes. ```java trigger = newTrigger() .withIdentity("trigger3", "group1") .startAt(tomorrowAt(15, 0, 0) // 15:00:00 tomorrow .withSchedule(calendarIntervalSchedule() .withIntervalInDays(2)) // interval is set in calendar days .build(); ``` -------------------------------- ### Set org.quartz.jobStore.class to RAMJobStore Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/configuration/ConfigRAMJobStore.html Selects RAMJobStore as the scheduler's job store by setting the 'org.quartz.jobStore.class' property. All scheduling information is stored in memory and lost when the process terminates. ```properties org.quartz.jobStore.class = org.quartz.simpl.RAMJobStore ``` -------------------------------- ### JobExceptionExample - Schedule BadJob1 with SimpleTrigger Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/examples/Example6.html Schedules BadJob1 to run every 3 seconds indefinitely using a SimpleTrigger with repeatForever(). ```java JobDetail job = newJob(BadJob1.class) .withIdentity("badJob1", "group1") .build(); SimpleTrigger trigger = newTrigger() .withIdentity("trigger1", "group1") .startAt(startTime) .withSchedule(simpleSchedule() .withIntervalInSeconds(3) .repeatForever()) .build(); Date ft = sched.scheduleJob(job, trigger); ``` -------------------------------- ### JobExceptionExample - Schedule BadJob2 with SimpleTrigger Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/examples/Example6.html Schedules BadJob2 to run every 3 seconds indefinitely using a SimpleTrigger with repeatForever(). ```java job = newJob(BadJob2.class) .withIdentity("badJob2", "group1") .build(); trigger = newTrigger() .withIdentity("trigger2", "group1") .startAt(startTime) .withSchedule(simpleSchedule() .withIntervalInSeconds(3) .repeatForever()) .build(); ft = sched.scheduleJob(job, trigger); ``` -------------------------------- ### Create Scheduler with StdSchedulerFactory Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/examples/Example14.html Creates a Scheduler instance using a specific Quartz properties file. The properties file configures a RAM-based scheduler with a single thread. ```java SchedulerFactory sf = new StdSchedulerFactory( "org/quartz/examples/example14/quartz_priority.properties"); Scheduler sched = sf.getScheduler(); ``` -------------------------------- ### Static imports for Quartz builder DSL Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/tutorials/tutorial-lesson-02.html Lists the static imports needed to use the Quartz builder DSL methods (JobBuilder, SimpleScheduleBuilder, CronScheduleBuilder, CalendarIntervalScheduleBuilder, TriggerBuilder, DateBuilder). ```java import static org.quartz.JobBuilder.*; import static org.quartz.SimpleScheduleBuilder.*; import static org.quartz.CronScheduleBuilder.*; import static org.quartz.CalendarIntervalScheduleBuilder.*; import static org.quartz.TriggerBuilder.*; import static org.quartz.DateBuilder.*; ``` -------------------------------- ### Configure JDBCJobStore with the Table Prefix Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/tutorials/tutorial-lesson-09.html Sets the tablePrefix property to QRTZ_ to inform the JobStore which table prefix is used. ```properties org.quartz.jobStore.tablePrefix = QRTZ_ ``` -------------------------------- ### Get Triggers of a Job with getTriggersOfJob Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/cookbook/JobTriggers.html Use this snippet to retrieve all triggers associated with a specific job. The job is identified by its name and group using the jobKey method. The method returns a List of Trigger objects. ```java List jobTriggers = sched.getTriggersOfJob(jobKey("jobName", "jobGroup")); ``` -------------------------------- ### Configure a Global JobListener Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/configuration/ConfigListeners.html Defines a global JobListener in the Quartz configuration file. The class must have a no-arg constructor, and properties are set reflectively with primitive data types (including Strings) supported. ```properties org.quartz.jobListener.NAME.class = com.foo.MyListenerClass org.quartz.jobListener.NAME.propName = propValue org.quartz.jobListener.NAME.prop2Name = prop2Value ``` -------------------------------- ### Configure XMLSchedulingDataProcessorPlugin in quartz.properties Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/cookbook/JobInitPlugin.html Excerpt from quartz.properties that enables the XMLSchedulingDataProcessorPlugin. The fileNames property points to jobs.xml; failOnFileNotFound controls exception on missing files; scanInterval sets reload interval in seconds (0 disables); wrapInUserTransaction should be true when using JobStoreCMT. ```java #=================================================== # Configure the Job Initialization Plugin #=================================================== org.quartz.plugin.jobInitializer.class = org.quartz.plugins.xml.XMLSchedulingDataProcessorPlugin org.quartz.plugin.jobInitializer.fileNames = jobs.xml org.quartz.plugin.jobInitializer.failOnFileNotFound = true org.quartz.plugin.jobInitializer.scanInterval = 10 org.quartz.plugin.jobInitializer.wrapInUserTransaction = false ``` -------------------------------- ### Create indexes on Quartz tables Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/faq.html SQL statements to create indexes on Quartz tables, especially on the TRIGGER table's NEXT_FIRE_TIME and TRIGGER_STATE fields, and on all columns of the FIRED_TRIGGERS table. These indexes can improve JDBCJobStore performance. ```sql create index idx_qrtz_t_next_fire_time on qrtz_triggers(NEXT_FIRE_TIME); create index idx_qrtz_t_state on qrtz_triggers(TRIGGER_STATE); create index idx_qrtz_t_nf_st on qrtz_triggers(TRIGGER_STATE,NEXT_FIRE_TIME); create index idx_qrtz_ft_trig_name on qrtz_fired_triggers(TRIGGER_NAME); create index idx_qrtz_ft_trig_group on qrtz_fired_triggers(TRIGGER_GROUP); create index idx_qrtz_ft_trig_name on qrtz_fired_triggers(TRIGGER_NAME); create index idx_qrtz_ft_trig_n_g on \ qrtz_fired_triggers(TRIGGER_NAME,TRIGGER_GROUP); create index idx_qrtz_ft_trig_inst_name on qrtz_fired_triggers(INSTANCE_NAME); create index idx_qrtz_ft_job_name on qrtz_fired_triggers(JOB_NAME); create index idx_qrtz_ft_job_group on qrtz_fired_triggers(JOB_GROUP); create index idx_qrtz_t_next_fire_time_misfire on \ qrtz_triggers(MISFIRE_INSTR,NEXT_FIRE_TIME); create index idx_qrtz_t_nf_st_misfire on \ qrtz_triggers(MISFIRE_INSTR,NEXT_FIRE_TIME,TRIGGER_STATE); create index idx_qrtz_t_nf_st_misfire_grp on \ qrtz_triggers(MISFIRE_INSTR,NEXT_FIRE_TIME,TRIGGER_GROUP,TRIGGER_STATE); ``` -------------------------------- ### CronTrigger Example 4 - fires every half hour between 8-10 am on the 5th and 20th of every month Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/tutorials/tutorial-lesson-06.html Cron expression that fires every half hour between 8 am and 10 am on the 5th and 20th of every month. Note: does not fire at 10:00 am. ```cron 0 0/30 8-9 5,20 * ? ``` -------------------------------- ### Putting data into JobDataMap while building JobDetail Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/tutorials/tutorial-lesson-03.html Shows how to add serializable data to JobDataMap using usingJobData() when building a JobDetail for DumbJob. ```java // define the job and tie it to our DumbJob class JobDetail job = newJob(DumbJob.class) .withIdentity("myJob", "group1") // name "myJob", group "group1" .usingJobData("jobSays", "Hello World!") .usingJobData("myFloatValue", 3.141f) .build(); ``` -------------------------------- ### Static imports for Quartz builders Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/tutorials/tutorial-lesson-06.html Static imports required for using TriggerBuilder, CronScheduleBuilder, and DateBuilder in a DSL-style. ```java import static org.quartz.TriggerBuilder.*; import static org.quartz.CronScheduleBuilder.*; import static org.quartz.DateBuilder.*: ``` -------------------------------- ### Implement JobListener interface Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/cookbook/JobListeners.html Create a custom JobListener by implementing the JobListener interface. The listener must provide a name and implement the three callback methods: jobToBeExecuted, jobWasExecuted, and jobExecutionVetoed. ```java package foo; import org.quartz.JobExecutionContext; import org.quartz.JobExecutionException; import org.quartz.JobListener; public class MyJobListener implements JobListener { private String name; public MyJobListener(String name) { this.name = name; } public String getName() { return name; } public void jobToBeExecuted(JobExecutionContext context) { // do something with the event } public void jobWasExecuted(JobExecutionContext context, JobExecutionException jobException) { // do something with the event } public void jobExecutionVetoed(JobExecutionContext context) { // do something with the event } } ``` -------------------------------- ### Static imports for TriggerBuilder, SimpleScheduleBuilder, and DateBuilder Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/tutorials/tutorial-lesson-05.html Required static imports to use the DSL-style builders for creating SimpleTrigger instances. ```java import static org.quartz.TriggerBuilder.*; import static org.quartz.SimpleScheduleBuilder.*; import static org.quartz.DateBuilder.*: ``` -------------------------------- ### Define job instance with JobDataMap Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/cookbook/DefineJobWithData.html Creates a JobDetail instance using the static newJob method, setting the job identity and adding a JobDataMap entry with usingJobData. This is the standard way to define a job with input data. ```java // Define job instance JobDetail job1 = newJob(MyJobClass.class) .withIdentity("job1", "group1") .usingJobData("someProp", "someValue") .build(); ``` -------------------------------- ### Static import for JobBuilder DSL Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/tutorials/tutorial-lesson-03.html Use this static import to enable the fluent DSL style when building JobDetail instances with JobBuilder. ```java import static org.quartz.JobBuilder.*; ``` -------------------------------- ### Set Job #1 parameters Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/examples/Example4.html Sets the favorite color to 'Green' and initializes the execution count to 1 for Job #1. ```java job1.getJobDataMap().put(ColorJob.FAVORITE_COLOR, "Green"); job1.getJobDataMap().put(ColorJob.EXECUTION_COUNT, 1); ``` -------------------------------- ### Configure a Global TriggerListener Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/configuration/ConfigListeners.html Defines a global TriggerListener in the Quartz configuration file. The class must have a no-arg constructor, and properties are set reflectively with primitive data types (including Strings) supported. ```properties org.quartz.triggerListener.NAME.class = com.foo.MyListenerClass org.quartz.triggerListener.NAME.propName = propValue org.quartz.triggerListener.NAME.prop2Name = prop2Value ``` -------------------------------- ### Build a trigger that will fire now, then repeat every five minutes, until the hour 22:00 Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/tutorials/tutorial-lesson-05.html Creates a trigger that fires immediately and repeats every 5 minutes until 22:00, using repeatForever() and endAt with DateBuilder's dateOf. ```java trigger = newTrigger() .withIdentity("trigger7", "group1") .withSchedule(simpleSchedule() .withIntervalInMinutes(5) .repeatForever()) .endAt(dateOf(22, 0, 0)) .build(); ``` -------------------------------- ### Configure JDBCJobStore with the name of the DataSource to use Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/tutorials/tutorial-lesson-09.html Sets the dataSource property to myDS, which must be defined elsewhere in the Quartz properties. ```properties org.quartz.jobStore.dataSource = myDS ``` -------------------------------- ### Set Job #2 parameters Source: https://www.quartz-scheduler.org/documentation/quartz-2.5.x/examples/Example4.html Sets the favorite color to 'Red' and initializes the execution count to 1 for Job #2. ```java job2.getJobDataMap().put(ColorJob.FAVORITE_COLOR, "Red"); job2.getJobDataMap().put(ColorJob.EXECUTION_COUNT, 1); ```