flowable/flowable-engine · error · FlowableException

Could not handle signal: process definition with id: " + pro

Error message

Could not handle signal: process definition with id: " + processDefinitionId + " is suspended for " + eventSubscription

What it means

SignalEventHandler routes a signal to a process-definition-level signal start event. If the target process definition is suspended, the signal cannot start a new instance, so Flowable throws this error naming the definition id and subscription. Suspended definitions cannot spawn process instances.

Source

Thrown at modules/flowable-engine/src/main/java/org/flowable/engine/impl/event/SignalEventHandler.java:55

    public String getEventHandlerType() {
        return EVENT_HANDLER_TYPE;
    }

    @SuppressWarnings("unchecked")
    @Override
    public void handleEvent(EventSubscriptionEntity eventSubscription, Object payload, CommandContext commandContext) {
        if (eventSubscription.getExecutionId() != null) {
            super.handleEvent(eventSubscription, payload, commandContext);

        } else if (eventSubscription.getProcessDefinitionId() != null) {

            // Find initial flow element matching the signal start event
            String processDefinitionId = eventSubscription.getProcessDefinitionId();
            org.flowable.bpmn.model.Process process = ProcessDefinitionUtil.getProcess(processDefinitionId);
            ProcessDefinition processDefinition = ProcessDefinitionUtil.getProcessDefinition(processDefinitionId);

            if (processDefinition.isSuspended()) {
                throw new FlowableException("Could not handle signal: process definition with id: " + processDefinitionId + " is suspended for " + eventSubscription);
            }

            // Start process instance via the flow element linked to the event
            FlowElement flowElement = process.getFlowElement(eventSubscription.getActivityId(), true);
            if (flowElement == null) {
                throw new FlowableException("Could not find matching FlowElement for " + eventSubscription);
            }

            ProcessInstanceHelper processInstanceHelper = CommandContextUtil.getProcessEngineConfiguration(commandContext).getProcessInstanceHelper();
            processInstanceHelper.createAndStartProcessInstanceWithInitialFlowElement(processDefinition, null, null, null, flowElement, process,
                    getPayloadAsMap(payload), null, null, null, true);

        } else if (eventSubscription.getScopeId() != null && ScopeTypes.CMMN.equals(eventSubscription.getScopeType())) {
            CommandContextUtil.getProcessEngineConfiguration(commandContext).getCaseInstanceService().handleSignalEvent(eventSubscription, getPayloadAsMap(payload));
        
        } else {
            throw new FlowableException("Invalid signal handling: no execution nor process definition set for " + eventSubscription);
        }

View on GitHub (pinned to d6d39ce1c6)

Solutions

  1. Resume the definition first: repositoryService.activateProcessDefinitionById(processDefinitionId) (or byKey), then resend the signal.
  2. If the signal should never target this definition, verify the signal name does not collide with a start-event subscription of a suspended process.
  3. Deploy a new active version of the definition if the old version was intentionally suspended.
  4. Catch FlowableException around signalEventReceived and queue the signal for later delivery after activation.

Example fix

// before
runtimeService.signalEventReceived("orderSignal");
// after
ProcessDefinition pd = repositoryService.createProcessDefinitionQuery()
    .processDefinitionKey("orderProcess").latestVersion().singleResult();
if (pd != null && pd.isSuspended()) {
    repositoryService.activateProcessDefinitionById(pd.getId(), true, null);
}
runtimeService.signalEventReceived("orderSignal");
Defensive patterns

Strategy: validation

Validate before calling

ProcessDefinition pd = repositoryService.createProcessDefinitionQuery()
    .processDefinitionKey(key).latestVersion().singleResult();
if (pd == null || pd.isSuspended()) {
    throw new IllegalStateException("Definition suspended, cannot deliver signal " + signalName);
}

Try / catch

try {
    runtimeService.signalEventReceived(signalName);
} catch (FlowableException e) {
    if (e.getMessage().contains("is suspended")) {
        signalRetryQueue.offer(signalName); // deliver after activation
    } else { throw e; }
}

Prevention

When it happens

Trigger: runtimeService.signalEventReceived(signalName, ...) or runtimeService.dispatchEvent for a signal whose EventSubscriptionEntity has a processDefinitionId whose ProcessDefinition.isSuspended() is true.

Common situations: A process definition was suspended (e.g. via RepositoryService.suspendProcessDefinitionById or suspendProcessDefinitionByKey including instances) while signal start events still had active subscriptions; scheduling signals during a maintenance suspension window.

Understand the failure class

Background: "Invalid state transition" errors: "status must be X, actually Y", "already rejected/charging/uninstalled", "cannot ... while running" — what they mean when a library rejects your call — this error's family across 31 libraries.

Related errors


AI-assisted analysis of flowable/flowable-engine@d6d39ce1c6 (2026-09-11). Data as JSON: /api/errors/168099afdca3d8b4. Report an issue: GitHub.