flowable/flowable-engine · error · FlowableIllegalArgumentException
token is null
Error message
token is null
What it means
SaveTokenCmd persists an authentication Token through the TokenEntityManager (insert for new tokens, update for existing). Since persistence requires an actual Token instance, a null argument is rejected with FlowableIllegalArgumentException.
Solutions
- Create the token first (identityService.newToken()) and populate it before saving
- Check the code path that produced the null token (lookup already returned nothing)
- Null-check before saving and skip or recreate the token accordingly
Example fix
// before
identityService.saveToken(token);
// after
if (token == null) {
token = identityService.newToken();
}
identityService.saveToken(token); Defensive patterns
Strategy: validation
Validate before calling
if (token == null) throw new IllegalArgumentException("token must not be null"); Type guard
boolean isSavableToken(Token t) { return t != null && t.getId() != null && !t.getId().trim().isEmpty(); } Try / catch
try { identityService.saveToken(token); } catch (FlowableIllegalArgumentException e) { log.error("Attempted to save null token", e); } Prevention
- Always create tokens via identityService.newToken() before saving
- Re-check token existence after purge/expiry jobs before re-saving
- Null-check tokens deserialized from external stores
When it happens
Trigger: Calling identityService.saveToken(null) or executing new SaveTokenCmd(config, null); also when a token variable from an earlier lookup/cleanup job is null at save time.
Common situations: Custom remember-me / token-store code that loads then saves a token which was already purged; deserialized token objects missing from request payloads.
Related errors
AI-assisted analysis of flowable/flowable-engine@d6d39ce1c6 (2026-09-11).
Data as JSON: /api/errors/7a80f06309340711.
Report an issue: GitHub.
Appendix: source
Thrown at modules/flowable-idm-engine/src/main/java/org/flowable/idm/engine/impl/cmd/SaveTokenCmd.java:45
* @author Tijs Rademakers
*/
public class SaveTokenCmd implements Command<Void>, Serializable {
private static final long serialVersionUID = 1L;
protected IdmEngineConfiguration idmEngineConfiguration;
protected Token token;
public SaveTokenCmd(Token token, IdmEngineConfiguration idmEngineConfiguration) {
this.token = token;
this.idmEngineConfiguration = idmEngineConfiguration;
}
@Override
public Void execute(CommandContext commandContext) {
if (token == null) {
throw new FlowableIllegalArgumentException("token is null");
}
if (idmEngineConfiguration.getTokenEntityManager().isNewToken(token)) {
if (token instanceof TokenEntity) {
idmEngineConfiguration.getTokenEntityManager().insert((TokenEntity) token, true);
} else {
CommandContextUtil.getDbSqlSession(commandContext).insert((Entity) token, idmEngineConfiguration.getIdGenerator());
}
} else {
idmEngineConfiguration.getTokenEntityManager().updateToken(token);
}
return null;
}
}
View on GitHub (pinned to d6d39ce1c6)