Make sure task is not executed after is has cancelled himself

This commit is contained in:
René Pfeuffer
2019-06-24 17:51:38 +02:00
parent eec4b282e6
commit 1e586b020c
3 changed files with 20 additions and 25 deletions

View File

@@ -30,7 +30,7 @@ final class CronExpression {
boolean shouldRun(ZonedDateTime time) { boolean shouldRun(ZonedDateTime time) {
ZonedDateTime now = ZonedDateTime.now(clock); ZonedDateTime now = ZonedDateTime.now(clock);
return time.isBefore(now); return time.isBefore(now) || time.isEqual(now);
} }
Optional<ZonedDateTime> calculateNextRun() { Optional<ZonedDateTime> calculateNextRun() {

View File

@@ -32,7 +32,7 @@ class CronTask implements Task, Runnable {
@Override @Override
public synchronized void run() { public synchronized void run() {
if (expression.shouldRun(nextRun)) { if (hasNextRun() && expression.shouldRun(nextRun)) {
LOG.debug("execute task {}, because of matching expression {}", name, expression); LOG.debug("execute task {}, because of matching expression {}", name, expression);
runnable.run(); runnable.run();
Optional<ZonedDateTime> next = expression.calculateNextRun(); Optional<ZonedDateTime> next = expression.calculateNextRun();
@@ -40,6 +40,7 @@ class CronTask implements Task, Runnable {
nextRun = next.get(); nextRun = next.get();
} else { } else {
LOG.debug("cancel task {}, because expression {} has no next execution", name, expression); LOG.debug("cancel task {}, because expression {} has no next execution", name, expression);
nextRun = null;
cancel(); cancel();
} }
} else { } else {

View File

@@ -53,7 +53,7 @@ class CronTaskTest {
@Test @Test
void shouldCancelWithoutNextRun() { void shouldCancelWithoutNextRun() {
ZonedDateTime time = ZonedDateTime.now(); ZonedDateTime time = ZonedDateTime.now();
when(expression.calculateNextRun()).thenAnswer(new FirstTimeAnswer(Optional.of(time), Optional.empty())); when(expression.calculateNextRun()).thenReturn(Optional.of(time), Optional.empty());
when(expression.shouldRun(time)).thenReturn(true); when(expression.shouldRun(time)).thenReturn(true);
CronTask task = task(); CronTask task = task();
@@ -64,32 +64,26 @@ class CronTaskTest {
verify(future).cancel(false); verify(future).cancel(false);
} }
@Test
void shouldNotRunAfterCancelHasBeenCalledIfRunIsCalledAgain() {
ZonedDateTime time = ZonedDateTime.now();
when(expression.calculateNextRun()).thenReturn(Optional.of(time), Optional.empty());
when(expression.shouldRun(time)).thenReturn(true);
CronTask task = task();
task.setFuture(future);
task.run();
task.run();
verify(future).cancel(false);
verify(runnable).run();
}
@Test @Test
void shouldNotRun() { void shouldNotRun() {
task().run(); task().run();
verify(runnable, never()).run(); verify(runnable, never()).run();
} }
private static class FirstTimeAnswer implements Answer<Object> {
private boolean first = true;
private final Object answer;
private final Object secondAnswer;
FirstTimeAnswer(Object answer, Object secondAnswer) {
this.answer = answer;
this.secondAnswer = secondAnswer;
}
@Override
public Object answer(InvocationOnMock invocation) {
if (first) {
first = false;
return answer;
}
return secondAnswer;
}
}
} }