flowable/flowable-engine · error · IllegalArgumentException
date object cannot be empty
Error message
date object cannot be empty
What it means
DateUtil.toDate converts DMN expression operands (Date, LocalDate, String, etc.) into java.util.Date. It throws IllegalArgumentException('date object cannot be empty') when the operand is null, because the engine cannot convert a missing value into a date for comparison in date-based DMN expressions.
Solutions
- Populate the date variable before decision-table evaluation (set it in the process or form data)
- Add a null check/default in the DMN expression, e.g. a ternary returning a default date
- Verify the input variable name in the decision table matches the supplied data key
- Validate input data before starting the process instance that evaluates the decision
Example fix
// before (unbound variable passed as date) after(creationDate, '2024-01-01') // after creationDate != null ? after(creationDate, '2024-01-01') : false
Defensive patterns
Strategy: validation
Validate before calling
if (dateValue == null) throw new IllegalArgumentException("date variable must be set before decision evaluation"); Type guard
boolean isDateLike(Object o) { return o instanceof java.util.Date || o instanceof org.joda.time.LocalDate || o instanceof java.time.temporal.TemporalAccessor || o instanceof String; } Try / catch
try { Date d = DateUtil.toDate(obj); } catch (IllegalArgumentException e) { d = defaultDate; } Prevention
- Ensure date variables are set in process/form data before the decision table runs
- Match variable names between expression and data source exactly
- Validate required date fields at data entry time
When it happens
Trigger: A DMN expression (e.g. before(date, x) / after(date, x) / date comparison in a decision table) receives null as its date operand, either as a literal null or from an unbound variable.
Common situations: Date input variables not set in the process/form; spelling mismatch between the variable name in the expression and the incoming data; test data missing a date field that production data has; deprecated Joda-Time LocalDate usage paths receiving null.
Related errors
- availableAfter is null
- availableBefore is null
- createdAfter is null
- createdBefore is null
- decisionKey is null
AI-assisted analysis of flowable/flowable-engine@d6d39ce1c6 (2026-09-11).
Data as JSON: /api/errors/e1d90ad88752ce72.
Report an issue: GitHub.
Appendix: source
Thrown at modules/flowable-dmn-engine/src/main/java/org/flowable/dmn/engine/impl/el/util/DateUtil.java:30
*/
package org.flowable.dmn.engine.impl.el.util;
import java.time.ZoneId;
import java.util.Date;
import org.flowable.common.engine.impl.joda.JodaDeprecationLogger;
import org.joda.time.LocalDate;
import org.joda.time.format.DateTimeFormat;
import org.joda.time.format.DateTimeFormatter;
/**
* @author Yvo Swillens
*/
public class DateUtil {
public static Date toDate(Object dateObject) {
if (dateObject == null) {
throw new IllegalArgumentException("date object cannot be empty");
}
if (dateObject instanceof Date) {
return (Date) dateObject;
} else if (dateObject instanceof LocalDate) {
JodaDeprecationLogger.LOGGER.warn("Using Joda-Time LocalDate has been deprecated and will be removed in a future version.");
return ((LocalDate) dateObject).toDate();
} else if (dateObject instanceof java.time.LocalDate) {
return Date.from(((java.time.LocalDate) dateObject).atStartOfDay()
.atZone(ZoneId.systemDefault())
.toInstant());
} else {
DateTimeFormatter dtf = DateTimeFormat.forPattern("yyyy-MM-dd");
LocalDate dateTime = dtf.parseLocalDate((String) dateObject);
return dateTime.toDate();
}
}
View on GitHub (pinned to d6d39ce1c6)