flowable/flowable-engine · error · ActivitiException
exception during timer execution: ${message}
Error message
exception during timer execution: ${message} What it means
Generic wrapper in TimerCatchIntermediateEventJobHandler.execute: any unexpected Exception while firing the timer (signal/execution continuation, event dispatch, etc.) is logged and rethrown as an ActivitiException whose message is the original exception's message, keeping the cause chain. It is a catch-all so timer failures surface with the underlying reason.
Source
Thrown at modules/flowable5-engine/src/main/java/org/activiti/engine/impl/jobexecutor/TimerCatchIntermediateEventJobHandler.java:69
commandContext.getEventDispatcher().dispatchEvent(
ActivitiEventBuilder.createEntityEvent(FlowableEngineEventType.TIMER_FIRED, job),
EngineConfigurationConstants.KEY_PROCESS_ENGINE_CONFIG);
}
if (!execution.getActivity().getId().equals(intermediateEventActivity.getId())) {
execution.setActivity(intermediateEventActivity);
}
execution.signal(null, null);
} catch (RuntimeException e) {
LogMDC.putMDCExecution(execution);
LOGGER.error("exception during timer execution", e);
LogMDC.clear();
throw e;
} catch (Exception e) {
LogMDC.putMDCExecution(execution);
LOGGER.error("exception during timer execution", e);
LogMDC.clear();
throw new ActivitiException("exception during timer execution: " + e.getMessage(), e);
}
}
}
View on GitHub (pinned to d6d39ce1c6)
Solutions
- Read the cause of the ActivitiException (getCause()) to find the real failure
- Check for concurrent modification: the process instance may have completed/moved past the timer before it fired
- Fix the underlying exception reported in the wrapped cause (dispatcher config, delegate, DB)
- Enable logging around TIMER_FIRED events to reproduce
Example fix
try {
managementService.executeJob(jobId);
} catch (FlowableException e) {
log.error("timer failed", e.getCause()); // real reason is the cause
} Defensive patterns
Strategy: try-catch
Try / catch
try {
managementService.executeJob(jobId);
} catch (FlowableException e) {
Throwable root = e; while (root.getCause() != null) root = root.getCause();
log.error("Timer execution failed, root cause: ", root); // act on the wrapped cause
} Prevention
- Always inspect getCause() — this error only mirrors the inner message
- Add retries with backoff for transient DB/concurrency failures during timer firing
- Monitor engine logs: the original exception is logged before rethrow
When it happens
Trigger: Any runtime exception thrown inside timer execution after the activity lookup succeeded: e.g. failures signaling the execution, event dispatcher errors, or delegate errors triggered during continuation.
Common situations: Execution already ended when timer fires (concurrent completion); event dispatcher misconfigured; downstream service task behind the timer fails; DB constraint issue while persisting the continuation.
Understand the failure class
Background: "This is a bug, please report it": internal invariant violations, unreachable panics, and SNH errors explained — this error's family across 47 libraries.
Related errors
- Error reading json value ${configuration}
- Error while firing timer: intermediate event activity ${nest
- Error converting timer expression
- Timer expression '${timerEventListener.getTimerExpression()}
- Could not find a job with id ''.
AI-assisted analysis of flowable/flowable-engine@d6d39ce1c6 (2026-09-11).
Data as JSON: /api/errors/bab3171ea1962865.
Report an issue: GitHub.