springboot integrates quartz and configures JNDI data sources

Keywords: Tomcat Java JDBC MySQL

rely on

<dependency>
	<groupId>org.springframework.boot</groupId>
	<artifactId>spring-boot-starter-logging</artifactId>
</dependency>

<dependency>
	<groupId>org.springframework.boot</groupId>
	<artifactId>spring-boot-starter-web</artifactId>
</dependency>

<dependency>
	<groupId>org.apache.tomcat.embed</groupId>
	<artifactId>tomcat-embed-core</artifactId>
</dependency>

<dependency>
	<groupId>org.springframework.boot</groupId>
	<artifactId>spring-boot-starter-quartz</artifactId>
</dependency>

<dependency>
	<groupId>mysql</groupId>
	<artifactId>mysql-connector-java</artifactId>
	<scope>runtime</scope>
</dependency>

<dependency>
	<groupId>com.mchange</groupId>
	<artifactId>c3p0</artifactId>
	<version>0.9.5.4</version>
</dependency>

application.yaml

spring:
  profiles:
    active: dev
      
  datasource:
    jndi-name: jdbc/mydb #Using jndi
#    url: jdbc:mysql://localhost:13306/demo
#    username: root
#    password: 123123
    
  # quartz configuration
  quartz:
    job-store-type: jdbc #Database Mode
    jdbc:    
      initialize-schema: embedded # embedded:(default), never: does not initialize the table structure, always: initializes the database every time it starts

Quartz profile: quartz.properties

# Fixed prefix org.quartz
# Mainly divided into scheduler, threadPool, jobStore, plugin and so on
#
#
org.quartz.scheduler.instanceName = DefaultQuartzScheduler
org.quartz.scheduler.rmi.export = false
org.quartz.scheduler.rmi.proxy = false
org.quartz.scheduler.wrapJobExecutionInUserTransaction = false

# When instantiating ThreadPool, the thread class used is SimpleThreadPool
org.quartz.threadPool.class = org.quartz.simpl.SimpleThreadPool

# threadCount and threadPriority inject ThreadPool instances as setter s
# Number of concurrencies
org.quartz.threadPool.threadCount = 5
# priority
org.quartz.threadPool.threadPriority = 5
org.quartz.threadPool.threadsInheritContextClassLoaderOfInitializingThread = true

org.quartz.jobStore.misfireThreshold = 5000

# Stored in memory by default
#org.quartz.jobStore.class = org.quartz.simpl.RAMJobStore

#Persistence
org.quartz.jobStore.class = org.quartz.impl.jdbcjobstore.JobStoreTX

org.quartz.jobStore.tablePrefix = qrtz_

org.quartz.jobStore.dataSource = qzDS

# Data source configuration qzDS is a custom name specified by the upper jobStore property
# The value of the jndiURL needs to be noted: some tutorials have jdbc/mydb filled in, which is actually the name of jndi, whereas the URL is clearly required here.
# So add JNDI before the JNDI name to provide the path to the container, and if the JNDI is applied on the same machine, fill in java:/comp/env/plus jndiName
org.quartz.dataSource.qzDS.jndiURL = java:/comp/env/jdbc/mydb

# Non-JDNI Configuration
#org.quartz.dataSource.qzDS.driver = com.mysql.cj.jdbc.Driver
#
#org.quartz.dataSource.qzDS.URL = jdbc:mysql://localhost:13306/demo
#
#org.quartz.dataSource.qzDS.user = root
#
#org.quartz.dataSource.qzDS.password = 123123
#
#org.quartz.dataSource.qzDS.maxConnections = 10

JNDI data source configuration Note: The org.quartz.dataSource.qzDS.jndiURL is configured with a JNDI URL instead of a Name.The data source in this example is provided by the embedded Tomcat and exposed as JNDI, so the embedded Tomcat configuration (springboot1.x is EmbeddedServletContainerCustomizer, 2.x is ServletWebServerFactory).This configuration is not required if it is run in a Tomcat container).

JNDI data source configuration (not required if the application is placed in a servlet container and the container is already configured with a JNDI data source)

DataSourceConfig.java


import javax.sql.DataSource;

import org.apache.catalina.Context;
import org.apache.catalina.startup.Tomcat;
import org.apache.tomcat.util.descriptor.web.ContextResource;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.boot.web.embedded.tomcat.TomcatServletWebServerFactory;
import org.springframework.boot.web.embedded.tomcat.TomcatWebServer;
import org.springframework.boot.web.servlet.server.ServletWebServerFactory;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Profile;

@Configuration
public class DataSourceConfig {
	
	@Value("${spring.datasource.jndi-name}")
	private String jndiName;

	@Profile("dev")
	@Bean
	public ServletWebServerFactory servletContainer() {
		TomcatServletWebServerFactory tomcat = new TomcatServletWebServerFactory() {
			@Override
			protected TomcatWebServer getTomcatWebServer(Tomcat tomcat) {
				tomcat.enableNaming();
				return super.getTomcatWebServer(tomcat);
			}

			@Override
			protected void postProcessContext(Context context) {
				
				System.out.println("stay Tomcat Add in JDNI:"+jndiName);

				ContextResource resource = new ContextResource();
				resource.setType(DataSource.class.getName());
				resource.setName(jndiName);
				resource.setProperty("factory", "com.zaxxer.hikari.HikariJNDIFactory");
				resource.setProperty("driverClassName", "com.mysql.cj.jdbc.Driver");
				resource.setProperty("jdbcUrl", "jdbc:mysql://localhost:13306/demo");
				resource.setProperty("username", "root");
				resource.setProperty("password", "123123");

				context.getNamingResources().addResource(resource);

			}
		};
		return tomcat;
	}
	
}

quartz configuration

QuartzConfig.java


import java.io.IOException;
import java.util.Properties;

import org.quartz.ee.servlet.QuartzInitializerListener;
import org.springframework.beans.factory.config.PropertiesFactoryBean;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.core.io.ClassPathResource;
import org.springframework.scheduling.annotation.EnableScheduling;
import org.springframework.scheduling.quartz.SchedulerFactoryBean;

import reactor.core.scheduler.Scheduler;

@Configuration
@EnableScheduling
public class QuartzConfig {


	/**
	 * Introduce Configuration
	 */
	@Bean
	public Properties quartzProperties() throws IOException {
		PropertiesFactoryBean propertiesFactoryBean = new PropertiesFactoryBean();
		propertiesFactoryBean.setLocation(new ClassPathResource("/quartz.properties"));
		// Initialize object after property is read and injected in quartz.properties
		propertiesFactoryBean.afterPropertiesSet();
		return propertiesFactoryBean.getObject();
	}

	/**
	 * quartz Initialize listener
	 */
	@Bean
	public QuartzInitializerListener executorListener() {
		return new QuartzInitializerListener();
	}

}

Quartz Service Class

QuartzService.java


import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Set;

import javax.annotation.PostConstruct;

import org.quartz.CronScheduleBuilder;
import org.quartz.CronTrigger;
import org.quartz.DateBuilder;
import org.quartz.DateBuilder.IntervalUnit;
import org.quartz.JobBuilder;
import org.quartz.JobDetail;
import org.quartz.JobExecutionContext;
import org.quartz.JobKey;
import org.quartz.Scheduler;
import org.quartz.SchedulerException;
import org.quartz.SchedulerFactory;
import org.quartz.SimpleScheduleBuilder;
import org.quartz.Trigger;
import org.quartz.TriggerBuilder;
import org.quartz.TriggerKey;
import org.quartz.impl.StdSchedulerFactory;
import org.quartz.impl.matchers.GroupMatcher;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.scheduling.quartz.QuartzJobBean;
import org.springframework.stereotype.Service;

@Service
public class QuartzService {

	private Scheduler scheduler;

	@PostConstruct
	public void startScheduler() {
		try {

			// 1. Create a factory class SchedulerFactory
			SchedulerFactory factory = new StdSchedulerFactory();
			// 2. Get an instance of Scheduler by the getScheduler() method
			scheduler = factory.getScheduler();

			scheduler.start();
		} catch (SchedulerException e) {
			e.printStackTrace();
		}
	}

	/**
	 * Add a job
	 *
	 * @param jobClass
	 *            Task Implementation Class
	 * @param jobName
	 *            Task Name
	 * @param jobGroupName
	 *            Task Group Name
	 * @param jobTime
	 *            Time expression (this is a task every few seconds)
	 * @param jobTimes
	 *            Number of runs (<0: unlimited)
	 * @param jobData
	 *            parameter
	 */
	public void addJob(Class<? extends QuartzJobBean> jobClass, String jobName, String jobGroupName, int jobTime,
			int jobTimes, Map jobData) {
		try {
			// Task name and group make up task key
			JobDetail jobDetail = JobBuilder.newJob(jobClass).withIdentity(jobName, jobGroupName).build();
			// Set job Parameters
			if (jobData != null && jobData.size() > 0) {
				jobDetail.getJobDataMap().putAll(jobData);
			}
			// Use the simpleTrigger rule
			Trigger trigger = null;
			if (jobTimes < 0) {
				trigger = TriggerBuilder.newTrigger().withIdentity(jobName, jobGroupName)
						.withSchedule(SimpleScheduleBuilder.repeatSecondlyForever(1).withIntervalInSeconds(jobTime))
						.startNow().build();
			} else {
				trigger = TriggerBuilder
						.newTrigger().withIdentity(jobName, jobGroupName).withSchedule(SimpleScheduleBuilder
								.repeatSecondlyForever(1).withIntervalInSeconds(jobTime).withRepeatCount(jobTimes))
						.startNow().build();
			}
			scheduler.scheduleJob(jobDetail, trigger);
		} catch (SchedulerException e) {
			e.printStackTrace();
		}
	}

	/**
	 * Add a job
	 *
	 * @param jobClass
	 *            Task Implementation Class
	 * @param jobName
	 *            Task Name (Recommended Unique)
	 * @param jobGroupName
	 *            Task Group Name
	 * @param jobTime
	 *            Time expressions (such as: 0/5 * * * *?)
	 * @param jobData
	 *            parameter
	 */
	public void addJob(Class<? extends QuartzJobBean> jobClass, String jobName, String jobGroupName, String jobTime,
			Map jobData) {
		try {
			// Create a jobDetail instance, bind the Job implementation class
			// Indicates the name of the job, the name of the group it belongs to, and the bound job class
			// Task name and group make up task key
			JobDetail jobDetail = JobBuilder.newJob(jobClass).withIdentity(jobName, jobGroupName).build();
			// Set job Parameters
			if (jobData != null && jobData.size() > 0) {
				jobDetail.getJobDataMap().putAll(jobData);
			}
			// Define Schedule Trigger Rules
			// Using the cornTrigger rule
			// Trigger key
			Trigger trigger = TriggerBuilder.newTrigger().withIdentity(jobName, jobGroupName)
					.startAt(DateBuilder.futureDate(1, IntervalUnit.SECOND))
					.withSchedule(CronScheduleBuilder.cronSchedule(jobTime)).startNow().build();
			// Register jobs and triggers in task scheduling
			scheduler.scheduleJob(jobDetail, trigger);
		} catch (Exception e) {
			e.printStackTrace();
		}
	}

	/**
	 * Modify a job's time expression
	 *
	 * @param jobName
	 * @param jobGroupName
	 * @param jobTime
	 */
	public void updateJob(String jobName, String jobGroupName, String jobTime) {
		try {
			TriggerKey triggerKey = TriggerKey.triggerKey(jobName, jobGroupName);
			CronTrigger trigger = (CronTrigger) scheduler.getTrigger(triggerKey);
			trigger = trigger.getTriggerBuilder().withIdentity(triggerKey)
					.withSchedule(CronScheduleBuilder.cronSchedule(jobTime)).build();
			// Restart Trigger
			scheduler.rescheduleJob(triggerKey, trigger);
		} catch (SchedulerException e) {
			e.printStackTrace();
		}
	}

	/**
	 * Delete Task One job
	 *
	 * @param jobName
	 *            Task Name
	 * @param jobGroupName
	 *            Task Group Name
	 */
	public void deleteJob(String jobName, String jobGroupName) {
		try {
			scheduler.deleteJob(new JobKey(jobName, jobGroupName));
		} catch (Exception e) {
			e.printStackTrace();
		}
	}

	/**
	 * Pause a job
	 *
	 * @param jobName
	 * @param jobGroupName
	 */
	public void pauseJob(String jobName, String jobGroupName) {
		try {
			JobKey jobKey = JobKey.jobKey(jobName, jobGroupName);
			scheduler.pauseJob(jobKey);
		} catch (SchedulerException e) {
			e.printStackTrace();
		}
	}

	/**
	 * Restore a job
	 *
	 * @param jobName
	 * @param jobGroupName
	 */
	public void resumeJob(String jobName, String jobGroupName) {
		try {
			JobKey jobKey = JobKey.jobKey(jobName, jobGroupName);
			scheduler.resumeJob(jobKey);
		} catch (SchedulerException e) {
			e.printStackTrace();
		}
	}

	/**
	 * Execute a job immediately
	 *
	 * @param jobName
	 * @param jobGroupName
	 */
	public void runAJobNow(String jobName, String jobGroupName) {
		try {
			JobKey jobKey = JobKey.jobKey(jobName, jobGroupName);
			scheduler.triggerJob(jobKey);
		} catch (SchedulerException e) {
			e.printStackTrace();
		}
	}

	/**
	 * Get a list of all scheduled tasks
	 *
	 * @return
	 */
	public List<Map<String, Object>> queryAllJob() {
		List<Map<String, Object>> jobList = null;
		try {
			GroupMatcher<JobKey> matcher = GroupMatcher.anyJobGroup();
			Set<JobKey> jobKeys = scheduler.getJobKeys(matcher);
			jobList = new ArrayList<Map<String, Object>>();
			for (JobKey jobKey : jobKeys) {
				List<? extends Trigger> triggers = scheduler.getTriggersOfJob(jobKey);
				for (Trigger trigger : triggers) {
					Map<String, Object> map = new HashMap<>();
					map.put("jobName", jobKey.getName());
					map.put("jobGroupName", jobKey.getGroup());
					map.put("description", "trigger:" + trigger.getKey());
					Trigger.TriggerState triggerState = scheduler.getTriggerState(trigger.getKey());
					map.put("jobStatus", triggerState.name());
					if (trigger instanceof CronTrigger) {
						CronTrigger cronTrigger = (CronTrigger) trigger;
						String cronExpression = cronTrigger.getCronExpression();
						map.put("jobTime", cronExpression);
					}
					jobList.add(map);
				}
			}
		} catch (SchedulerException e) {
			e.printStackTrace();
		}
		return jobList;
	}

	/**
	 * Get all running job s
	 *
	 * @return
	 */
	public List<Map<String, Object>> queryRunJob() {
		List<Map<String, Object>> jobList = null;
		try {
			List<JobExecutionContext> executingJobs = scheduler.getCurrentlyExecutingJobs();
			jobList = new ArrayList<Map<String, Object>>(executingJobs.size());
			for (JobExecutionContext executingJob : executingJobs) {
				Map<String, Object> map = new HashMap<String, Object>();
				JobDetail jobDetail = executingJob.getJobDetail();
				JobKey jobKey = jobDetail.getKey();
				Trigger trigger = executingJob.getTrigger();
				map.put("jobName", jobKey.getName());
				map.put("jobGroupName", jobKey.getGroup());
				map.put("description", "trigger:" + trigger.getKey());
				Trigger.TriggerState triggerState = scheduler.getTriggerState(trigger.getKey());
				map.put("jobStatus", triggerState.name());
				if (trigger instanceof CronTrigger) {
					CronTrigger cronTrigger = (CronTrigger) trigger;
					String cronExpression = cronTrigger.getCronExpression();
					map.put("jobTime", cronExpression);
				}
				jobList.add(map);
			}
		} catch (SchedulerException e) {
			e.printStackTrace();
		}
		return jobList;
	}
}

test

MyJob.java

import org.quartz.JobDataMap;
import org.quartz.JobExecutionContext;
import org.quartz.JobExecutionException;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.scheduling.quartz.QuartzJobBean;

public class MyJob extends QuartzJobBean {
	
	Logger log = LoggerFactory.getLogger(MyJob.class);
	
    @Override
    protected void executeInternal(JobExecutionContext jobExecutionContext) throws JobExecutionException {
        // Get parameters
        JobDataMap jobDataMap = jobExecutionContext.getJobDetail().getJobDataMap();
        // Business Logic...
        log.info("------springbootquartzonejob implement"+jobDataMap.get("name").toString()+"###############"+jobExecutionContext.getTrigger());

    }
}

QuartzController.java


import java.util.HashMap;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;

import com.demo.quartz.MyJob;
import com.demo.quartz.QuartzService;

@Controller
@RequestMapping("/quartz")
public class QuartzController {

	@Autowired
	QuartzService quartzService;

	@RequestMapping("test")
	public String test() {

		HashMap<String, Object> map = new HashMap<>();
		map.put("name", 1);
		quartzService.deleteJob("job", "test");
		quartzService.addJob(MyJob.class, "job", "test", "0 * * * * ?", map);

		map.put("name", 2);
		quartzService.deleteJob("job2", "test");
		quartzService.addJob(MyJob.class, "job2", "test", "10 * * * * ?", map);

		map.put("name", 3);
		quartzService.deleteJob("job3", "test2");
		quartzService.addJob(MyJob.class, "job3", "test2", "15 * * * * ?", map);

		return "OK";
	}

}

Data Table Structure

CREATE TABLE QRTZ_JOB_DETAILS(  
SCHED_NAME VARCHAR(120) NOT NULL,  
JOB_NAME VARCHAR(200) NOT NULL,  
JOB_GROUP VARCHAR(200) NOT NULL,  
DESCRIPTION VARCHAR(250) NULL,  
JOB_CLASS_NAME VARCHAR(250) NOT NULL,  
IS_DURABLE VARCHAR(1) NOT NULL,  
IS_NONCONCURRENT VARCHAR(1) NOT NULL,  
IS_UPDATE_DATA VARCHAR(1) NOT NULL,  
REQUESTS_RECOVERY VARCHAR(1) NOT NULL,  
JOB_DATA BLOB NULL,  
PRIMARY KEY (SCHED_NAME,JOB_NAME,JOB_GROUP))  
ENGINE=InnoDB;  
  
CREATE TABLE QRTZ_TRIGGERS (  
SCHED_NAME VARCHAR(120) NOT NULL,  
TRIGGER_NAME VARCHAR(200) NOT NULL,  
TRIGGER_GROUP VARCHAR(200) NOT NULL,  
JOB_NAME VARCHAR(200) NOT NULL,  
JOB_GROUP VARCHAR(200) NOT NULL,  
DESCRIPTION VARCHAR(250) NULL,  
NEXT_FIRE_TIME BIGINT(13) NULL,  
PREV_FIRE_TIME BIGINT(13) NULL,  
PRIORITY INTEGER NULL,  
TRIGGER_STATE VARCHAR(16) NOT NULL,  
TRIGGER_TYPE VARCHAR(8) NOT NULL,  
START_TIME BIGINT(13) NOT NULL,  
END_TIME BIGINT(13) NULL,  
CALENDAR_NAME VARCHAR(200) NULL,  
MISFIRE_INSTR SMALLINT(2) NULL,  
JOB_DATA BLOB NULL,  
PRIMARY KEY (SCHED_NAME,TRIGGER_NAME,TRIGGER_GROUP),  
FOREIGN KEY (SCHED_NAME,JOB_NAME,JOB_GROUP)  
REFERENCES QRTZ_JOB_DETAILS(SCHED_NAME,JOB_NAME,JOB_GROUP))  
ENGINE=InnoDB;  
  
CREATE TABLE QRTZ_SIMPLE_TRIGGERS (  
SCHED_NAME VARCHAR(120) NOT NULL,  
TRIGGER_NAME VARCHAR(200) NOT NULL,  
TRIGGER_GROUP VARCHAR(200) NOT NULL,  
REPEAT_COUNT BIGINT(7) NOT NULL,  
REPEAT_INTERVAL BIGINT(12) NOT NULL,  
TIMES_TRIGGERED BIGINT(10) NOT NULL,  
PRIMARY KEY (SCHED_NAME,TRIGGER_NAME,TRIGGER_GROUP),  
FOREIGN KEY (SCHED_NAME,TRIGGER_NAME,TRIGGER_GROUP)  
REFERENCES QRTZ_TRIGGERS(SCHED_NAME,TRIGGER_NAME,TRIGGER_GROUP))  
ENGINE=InnoDB;  
  
CREATE TABLE QRTZ_CRON_TRIGGERS (  
SCHED_NAME VARCHAR(120) NOT NULL,  
TRIGGER_NAME VARCHAR(200) NOT NULL,  
TRIGGER_GROUP VARCHAR(200) NOT NULL,  
CRON_EXPRESSION VARCHAR(120) NOT NULL,  
TIME_ZONE_ID VARCHAR(80),  
PRIMARY KEY (SCHED_NAME,TRIGGER_NAME,TRIGGER_GROUP),  
FOREIGN KEY (SCHED_NAME,TRIGGER_NAME,TRIGGER_GROUP)  
REFERENCES QRTZ_TRIGGERS(SCHED_NAME,TRIGGER_NAME,TRIGGER_GROUP))  
ENGINE=InnoDB;  
  
CREATE TABLE QRTZ_SIMPROP_TRIGGERS  
  (
    SCHED_NAME VARCHAR(120) NOT NULL,  
    TRIGGER_NAME VARCHAR(200) NOT NULL,  
    TRIGGER_GROUP VARCHAR(200) NOT NULL,  
    STR_PROP_1 VARCHAR(512) NULL,  
    STR_PROP_2 VARCHAR(512) NULL,  
    STR_PROP_3 VARCHAR(512) NULL,  
    INT_PROP_1 INT NULL,  
    INT_PROP_2 INT NULL,  
    LONG_PROP_1 BIGINT NULL,  
    LONG_PROP_2 BIGINT NULL,  
    DEC_PROP_1 NUMERIC(13,4) NULL,  
    DEC_PROP_2 NUMERIC(13,4) NULL,  
    BOOL_PROP_1 VARCHAR(1) NULL,  
    BOOL_PROP_2 VARCHAR(1) NULL,  
    PRIMARY KEY (SCHED_NAME,TRIGGER_NAME,TRIGGER_GROUP),  
    FOREIGN KEY (SCHED_NAME,TRIGGER_NAME,TRIGGER_GROUP)   
    REFERENCES QRTZ_TRIGGERS(SCHED_NAME,TRIGGER_NAME,TRIGGER_GROUP))  
ENGINE=InnoDB;  
  
CREATE TABLE QRTZ_BLOB_TRIGGERS (  
SCHED_NAME VARCHAR(120) NOT NULL,  
TRIGGER_NAME VARCHAR(200) NOT NULL,  
TRIGGER_GROUP VARCHAR(200) NOT NULL,  
BLOB_DATA BLOB NULL,  
PRIMARY KEY (SCHED_NAME,TRIGGER_NAME,TRIGGER_GROUP),  
INDEX (SCHED_NAME,TRIGGER_NAME, TRIGGER_GROUP),  
FOREIGN KEY (SCHED_NAME,TRIGGER_NAME,TRIGGER_GROUP)  
REFERENCES QRTZ_TRIGGERS(SCHED_NAME,TRIGGER_NAME,TRIGGER_GROUP))  
ENGINE=InnoDB;  
  
CREATE TABLE QRTZ_CALENDARS (  
SCHED_NAME VARCHAR(120) NOT NULL,  
CALENDAR_NAME VARCHAR(200) NOT NULL,  
CALENDAR BLOB NOT NULL,  
PRIMARY KEY (SCHED_NAME,CALENDAR_NAME))  
ENGINE=InnoDB;  
  
CREATE TABLE QRTZ_PAUSED_TRIGGER_GRPS (  
SCHED_NAME VARCHAR(120) NOT NULL,  
TRIGGER_GROUP VARCHAR(200) NOT NULL,  
PRIMARY KEY (SCHED_NAME,TRIGGER_GROUP))  
ENGINE=InnoDB;  
  
CREATE TABLE QRTZ_FIRED_TRIGGERS (  
SCHED_NAME VARCHAR(120) NOT NULL,  
ENTRY_ID VARCHAR(95) NOT NULL,  
TRIGGER_NAME VARCHAR(200) NOT NULL,  
TRIGGER_GROUP VARCHAR(200) NOT NULL,  
INSTANCE_NAME VARCHAR(200) NOT NULL,  
FIRED_TIME BIGINT(13) NOT NULL,  
SCHED_TIME BIGINT(13) NOT NULL,  
PRIORITY INTEGER NOT NULL,  
STATE VARCHAR(16) NOT NULL,  
JOB_NAME VARCHAR(200) NULL,  
JOB_GROUP VARCHAR(200) NULL,  
IS_NONCONCURRENT VARCHAR(1) NULL,  
REQUESTS_RECOVERY VARCHAR(1) NULL,  
PRIMARY KEY (SCHED_NAME,ENTRY_ID))  
ENGINE=InnoDB;  
  
CREATE TABLE QRTZ_SCHEDULER_STATE (  
SCHED_NAME VARCHAR(120) NOT NULL,  
INSTANCE_NAME VARCHAR(200) NOT NULL,  
LAST_CHECKIN_TIME BIGINT(13) NOT NULL,  
CHECKIN_INTERVAL BIGINT(13) NOT NULL,  
PRIMARY KEY (SCHED_NAME,INSTANCE_NAME))  
ENGINE=InnoDB;  
  
CREATE TABLE QRTZ_LOCKS (  
SCHED_NAME VARCHAR(120) NOT NULL,  
LOCK_NAME VARCHAR(40) NOT NULL,  
PRIMARY KEY (SCHED_NAME,LOCK_NAME))  
ENGINE=InnoDB;  
  
CREATE INDEX IDX_QRTZ_J_REQ_RECOVERY ON QRTZ_JOB_DETAILS(SCHED_NAME,REQUESTS_RECOVERY);  
CREATE INDEX IDX_QRTZ_J_GRP ON QRTZ_JOB_DETAILS(SCHED_NAME,JOB_GROUP);  
  
CREATE INDEX IDX_QRTZ_T_J ON QRTZ_TRIGGERS(SCHED_NAME,JOB_NAME,JOB_GROUP);  
CREATE INDEX IDX_QRTZ_T_JG ON QRTZ_TRIGGERS(SCHED_NAME,JOB_GROUP);  
CREATE INDEX IDX_QRTZ_T_C ON QRTZ_TRIGGERS(SCHED_NAME,CALENDAR_NAME);  
CREATE INDEX IDX_QRTZ_T_G ON QRTZ_TRIGGERS(SCHED_NAME,TRIGGER_GROUP);  
CREATE INDEX IDX_QRTZ_T_STATE ON QRTZ_TRIGGERS(SCHED_NAME,TRIGGER_STATE);  
CREATE INDEX IDX_QRTZ_T_N_STATE ON QRTZ_TRIGGERS(SCHED_NAME,TRIGGER_NAME,TRIGGER_GROUP,TRIGGER_STATE);  
CREATE INDEX IDX_QRTZ_T_N_G_STATE ON QRTZ_TRIGGERS(SCHED_NAME,TRIGGER_GROUP,TRIGGER_STATE);  
CREATE INDEX IDX_QRTZ_T_NEXT_FIRE_TIME ON QRTZ_TRIGGERS(SCHED_NAME,NEXT_FIRE_TIME);  
CREATE INDEX IDX_QRTZ_T_NFT_ST ON QRTZ_TRIGGERS(SCHED_NAME,TRIGGER_STATE,NEXT_FIRE_TIME);  
CREATE INDEX IDX_QRTZ_T_NFT_MISFIRE ON QRTZ_TRIGGERS(SCHED_NAME,MISFIRE_INSTR,NEXT_FIRE_TIME);  
CREATE INDEX IDX_QRTZ_T_NFT_ST_MISFIRE ON QRTZ_TRIGGERS(SCHED_NAME,MISFIRE_INSTR,NEXT_FIRE_TIME,TRIGGER_STATE);  
CREATE INDEX IDX_QRTZ_T_NFT_ST_MISFIRE_GRP ON QRTZ_TRIGGERS(SCHED_NAME,MISFIRE_INSTR,NEXT_FIRE_TIME,TRIGGER_GROUP,TRIGGER_STATE);  
  
CREATE INDEX IDX_QRTZ_FT_TRIG_INST_NAME ON QRTZ_FIRED_TRIGGERS(SCHED_NAME,INSTANCE_NAME);  
CREATE INDEX IDX_QRTZ_FT_INST_JOB_REQ_RCVRY ON QRTZ_FIRED_TRIGGERS(SCHED_NAME,INSTANCE_NAME,REQUESTS_RECOVERY);  
CREATE INDEX IDX_QRTZ_FT_J_G ON QRTZ_FIRED_TRIGGERS(SCHED_NAME,JOB_NAME,JOB_GROUP);  
CREATE INDEX IDX_QRTZ_FT_JG ON QRTZ_FIRED_TRIGGERS(SCHED_NAME,JOB_GROUP);  
CREATE INDEX IDX_QRTZ_FT_T_G ON QRTZ_FIRED_TRIGGERS(SCHED_NAME,TRIGGER_NAME,TRIGGER_GROUP);  
CREATE INDEX IDX_QRTZ_FT_TG ON QRTZ_FIRED_TRIGGERS(SCHED_NAME,TRIGGER_GROUP); 
  • surface
Table Name Explain
qrtz_calendars Store Quartz's alendar information in Blob type
qrtz_cron_triggers Stores CronTrigger, including Cron expressions and time zone information
qrtz_fired_triggers Stores status information related to triggered Trigger s and execution information for associated Job s
qrtz_paused_trigger_grps Stores information about suspended Trigger groups
qrtz_scheduler_state Stores a small number of states about the Scheduler and other Scheduler instances (if used in a cluster)
qrtz_locks Stored program non-pessimistic lock information (if a pessimistic lock is used)
qrtz_job_details Store details of each configured Job (jobDetail)
qrtz_job_listeners Stores information about configured Job listeners
qrtz_simple_triggers Store simple Trigger s, including repetitions, intervals, and touches
qrtz_blog_triggers Triggers stored in Blob type (when Quartz users create their own custom Trigger type with JDBC and JobStore doesn't know how to store instances)
qrtz_trigger_listeners Stores information about the configured TriggerListener
qrtz_triggers Stores information about configured triggers (Triggers)

Table structure description

  • Table qrtz_job_details: Saves job details, which require user initialization as appropriate

job_name: The name of a job in a cluster, which can be customized by the user himself without any compulsory requirement. job_group: The name of the group to which the job belongs in the cluster, which is customized by the user himself without compulsory requirement. job_class_name: The full package name of a note job implementation class in the cluster. quartz finds the job class is_durable: persistent or not based on this path.Property set to 1, quartz persists job to database job_data: a blob field that holds persisted job objects

  • Table qrtz_triggers: Save trigger information trigger_name: trigger name, the name of the name user can customize at will, no mandatory requirements trigger_group:trigger belongs to the group name, the name user can customize at will, no mandatory requirements job_name: qrtz_job_details table job_name foreign key job_group: qrtz_job_details table job_group foreign key trigger_state:Pretrigger state, (WAITING: Wait for PAUSED: Pause ACQUIRED: Perform BLOCKED normally: Block ERROR: Error.trigger_type: Trigger type, CRON, SIMPLE

  • Table qrtz_cron_triggers: Foreign key to store cron expression table trigger_name: qrtz_triggers table trigger_name trigger_group: foreign key to qrtz_triggers table trigger_group cron_expression:cron expression

  • Table qrtz_scheduler_state: Stores information about note instances in the cluster, which quartz periodically reads to determine the current state of each instance in the cluster instance_name: The name of the org.quartz.scheduler.instanceId configuration in the previous configuration file is written to that field, and if set to AUTO,quartz generates a name based on the physical machine name and current time, last_checkin_time:Last check time checkin_interval:Check interval time

Posted by n8r0x on Tue, 24 Dec 2019 19:15:05 -0800