Details
diff --git a/azkaban-web-server/src/main/java/azkaban/scheduler/QuartzScheduler.java b/azkaban-web-server/src/main/java/azkaban/scheduler/QuartzScheduler.java
index 179b1f6..28f917d 100644
--- a/azkaban-web-server/src/main/java/azkaban/scheduler/QuartzScheduler.java
+++ b/azkaban-web-server/src/main/java/azkaban/scheduler/QuartzScheduler.java
@@ -18,6 +18,7 @@ package azkaban.scheduler;
import static java.util.Objects.requireNonNull;
+import azkaban.Constants.ConfigurationKeys;
import azkaban.utils.Props;
import java.util.Set;
import javax.inject.Inject;
@@ -37,8 +38,7 @@ import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
/**
- * Manages Quartz schedules. Azkaban regards QuartzJob and QuartzTrigger as an one-to-one
- * mapping.
+ * Manages Quartz schedules. Azkaban regards QuartzJob and QuartzTrigger as an one-to-one mapping.
*/
@Singleton
public class QuartzScheduler {
@@ -49,7 +49,10 @@ public class QuartzScheduler {
private Scheduler scheduler = null;
@Inject
- public QuartzScheduler(final Props azProps) throws SchedulerException{
+ public QuartzScheduler(final Props azProps) throws SchedulerException {
+ if (!azProps.getBoolean(ConfigurationKeys.ENABLE_QUARTZ, false)) {
+ return;
+ }
final StdSchedulerFactory schedulerFactory =
new StdSchedulerFactory(azProps.toProperties());
this.scheduler = schedulerFactory.getScheduler();
@@ -101,7 +104,7 @@ public class QuartzScheduler {
}
public void unregisterJob(final String groupName) throws SchedulerException {
- if(!ifJobExist(groupName)) {
+ if (!ifJobExist(groupName)) {
logger.warn("can not find job with " + groupName + " in quartz.");
} else {
this.scheduler.deleteJob(new JobKey(DEFAULT_JOB_NAME, groupName));
@@ -113,27 +116,26 @@ public class QuartzScheduler {
*
* @param cronExpression the cron schedule for this job
* @param jobDescription Regarding QuartzJobDescription#groupName, in order to guarantee no
- * duplicate quartz schedules, we design the naming convention depending on use cases:
- * <ul>
- * <li>User flow schedule: we use {@link org.quartz.JobKey#JobKey} to represent the identity
- * of a flow's schedule. The format follows "$projectID_$flowName" to guarantee no duplicates.
- * </li>
- * <li>Quartz schedule for AZ internal use: the groupName should start with letters, rather
- * than number, which is the first case. </li>
- * <ul>
+ * duplicate quartz schedules, we design the naming convention depending on use cases: <ul>
+ * <li>User flow schedule: we use {@link org.quartz.JobKey#JobKey} to represent the identity of a
+ * flow's schedule. The format follows "$projectID_$flowName" to guarantee no duplicates.
+ * <li>Quartz schedule for AZ internal use: the groupName should start with letters, rather than
+ * number, which is the first case.</ul>
*/
public void registerJob(final String cronExpression, final QuartzJobDescription jobDescription)
- throws SchedulerException {
+ throws SchedulerException {
requireNonNull(jobDescription, "jobDescription is null");
// Not allowed to register duplicate job name.
- if(ifJobExist(jobDescription.getGroupName())) {
- throw new SchedulerException("can not register existing job " + jobDescription.getGroupName());
+ if (ifJobExist(jobDescription.getGroupName())) {
+ throw new SchedulerException(
+ "can not register existing job " + jobDescription.getGroupName());
}
if (!CronExpression.isValidExpression(cronExpression)) {
- throw new SchedulerException("The cron expression string <" + cronExpression + "> is not valid.");
+ throw new SchedulerException(
+ "The cron expression string <" + cronExpression + "> is not valid.");
}
// TODO kunkun-tang: we will modify this when we start supporting multi schedules per flow.
diff --git a/azkaban-web-server/src/main/java/azkaban/webapp/AzkabanWebServer.java b/azkaban-web-server/src/main/java/azkaban/webapp/AzkabanWebServer.java
index cb73909..943fca4 100644
--- a/azkaban-web-server/src/main/java/azkaban/webapp/AzkabanWebServer.java
+++ b/azkaban-web-server/src/main/java/azkaban/webapp/AzkabanWebServer.java
@@ -231,7 +231,9 @@ public class AzkabanWebServer extends AzkabanServer {
@Override
public void run() {
try {
- webServer.quartzScheduler.shutdown();
+ if (webServer.quartzScheduler != null) {
+ webServer.quartzScheduler.shutdown();
+ }
} catch (final Exception e) {
logger.error(("Exception while shutting down quartz scheduler."), e);
}
@@ -520,8 +522,7 @@ public class AzkabanWebServer extends AzkabanServer {
startWebMetrics();
}
- if(this.props.containsKey(ConfigurationKeys.ENABLE_QUARTZ) && this.props.getBoolean(ConfigurationKeys
- .ENABLE_QUARTZ)) {
+ if (this.props.getBoolean(ConfigurationKeys.ENABLE_QUARTZ, false)) {
this.quartzScheduler.start();
}
diff --git a/azkaban-web-server/src/test/java/azkaban/scheduler/QuartzSchedulerTest.java b/azkaban-web-server/src/test/java/azkaban/scheduler/QuartzSchedulerTest.java
index 0e97f61..aae8ddf 100644
--- a/azkaban-web-server/src/test/java/azkaban/scheduler/QuartzSchedulerTest.java
+++ b/azkaban-web-server/src/test/java/azkaban/scheduler/QuartzSchedulerTest.java
@@ -19,6 +19,7 @@ package azkaban.scheduler;
import static org.assertj.core.api.Assertions.assertThat;
import static org.assertj.core.api.Assertions.assertThatThrownBy;
+import azkaban.Constants.ConfigurationKeys;
import azkaban.db.AzDBTestUtility;
import azkaban.db.DatabaseOperator;
import azkaban.test.TestUtils;
@@ -31,6 +32,7 @@ import org.junit.After;
import org.junit.AfterClass;
import org.junit.Before;
import org.junit.BeforeClass;
+import org.junit.Ignore;
import org.junit.Test;
import org.quartz.SchedulerException;
@@ -45,10 +47,11 @@ public class QuartzSchedulerTest {
@BeforeClass
public static void setUpQuartz() throws Exception {
dbOperator = AzDBTestUtility.initQuartzDB();
- final String quartzPropsPath=
+ final String quartzPropsPath =
new File("../azkaban-web-server/src/test/resources/quartz.test.properties")
- .getCanonicalPath();
+ .getCanonicalPath();
final Props quartzProps = new Props(null, quartzPropsPath);
+ quartzProps.put(ConfigurationKeys.ENABLE_QUARTZ, "true");
scheduler = new QuartzScheduler(quartzProps);
scheduler.start();
}
@@ -75,7 +78,7 @@ public class QuartzSchedulerTest {
}
@Test
- public void testCreateScheduleAndRun() throws Exception{
+ public void testCreateScheduleAndRun() throws Exception {
scheduler.registerJob("* * * * * ?", createJobDescription());
assertThat(scheduler.ifJobExist("SampleService")).isEqualTo(true);
TestUtils.await().untilAsserted(() -> assertThat(SampleQuartzJob.COUNT_EXECUTION)
@@ -83,7 +86,7 @@ public class QuartzSchedulerTest {
}
@Test
- public void testNotAllowDuplicateJobRegister() throws Exception{
+ public void testNotAllowDuplicateJobRegister() throws Exception {
scheduler.registerJob("* * * * * ?", createJobDescription());
assertThatThrownBy(
() -> scheduler.registerJob("0 5 * * * ?", createJobDescription()))
@@ -92,7 +95,7 @@ public class QuartzSchedulerTest {
}
@Test
- public void testInvalidCron() throws Exception{
+ public void testInvalidCron() throws Exception {
assertThatThrownBy(
() -> scheduler.registerJob("0 5 * * * *", createJobDescription()))
.isInstanceOf(SchedulerException.class)
@@ -100,15 +103,16 @@ public class QuartzSchedulerTest {
}
@Test
- public void testUnregisterSchedule() throws Exception{
+ public void testUnregisterSchedule() throws Exception {
scheduler.registerJob("* * * * * ?", createJobDescription());
assertThat(scheduler.ifJobExist("SampleService")).isEqualTo(true);
scheduler.unregisterJob("SampleService");
assertThat(scheduler.ifJobExist("SampleService")).isEqualTo(false);
}
+ @Ignore("Flaky test, slow too. Don't use Thread.sleep in unit tests.")
@Test
- public void testPauseAndResume() throws Exception{
+ public void testPauseAndResume() throws Exception {
scheduler.registerJob("* * * * * ?", createJobDescription());
scheduler.pause();
final int count = SampleQuartzJob.COUNT_EXECUTION;