mastra-ai/mastra · error
No active agent run found for signal target
Error message
No active agent run found for signal target
What it means
Thrown by the signal-sending path (sendSignal / signal APIs) when no resourceId/threadId can be resolved from the target or from an active run record, i.e. there is no active agent run matching the signal target. The runtime cannot determine which thread the signal belongs to.
Source
Thrown at packages/core/src/agent/thread-stream-runtime.ts:2811
} else {
// Stale cross-pod entry. Clean it up from the local map, then let the lease decide
state.activeThreadRunIds.delete(key);
state.activeThreadStreamIds.delete(key);
}
}
}
if (runId) {
activeRecord ??= state.threadRunsById.get(runId);
if (activeRecord) {
key ??= this.#threadKey(activeRecord.resourceId, activeRecord.threadId);
}
}
const resourceId = target.resourceId ?? activeRecord?.resourceId;
const threadId = target.threadId ?? activeRecord?.threadId;
if (!resourceId || !threadId) {
throw new Error('No active agent run found for signal target');
}
const isActiveTarget = Boolean(
runId && (activeRecord?.output.status === 'running' || (key && state.activeThreadRunIds.get(key) === runId)),
);
let signal = createSignal({
...signalInput,
id: signalInput.id ?? this.#generateSignalMessageId(agent, { resourceId, threadId }),
acceptedAt: new Date(),
});
// Resolve conditional delivery attributes now that we know the delivery path.
signal = resolveDeliveryAttributes(
signal,
isActiveTarget ? target.ifActive?.attributes : target.ifIdle?.attributes,
);
if (isActiveTarget && activeBehavior !== 'deliver') {View on GitHub (pinned to 75dd419e61)
Solutions
- Pass explicit resourceId and threadId in the target instead of relying on an active run lookup.
- Before signaling, confirm the run is still active (e.g. check run status) and handle the finished-run case.
- Use ifIdle options so the signal has a defined idle-path target with full thread IDs.
Example fix
// before
await runtime.sendSignal(agent, signalInput, { runId }); // run may be gone
// after
await runtime.sendSignal(agent, signalInput, { runId, resourceId: 'user-1', threadId: 'thread-1' }); Defensive patterns
Strategy: validation
Validate before calling
if (!target.resourceId || !target.threadId) {
// resolve from your own run registry before signaling
const rec = myRuns.get(target.runId);
if (!rec || rec.status !== 'running') throw new Error('No active run for signal target');
target.resourceId ??= rec.resourceId;
target.threadId ??= rec.threadId;
} Type guard
null
Try / catch
try {
return await runtime.sendSignal(agent, input, target);
} catch (e) {
if (e instanceof Error && e.message === 'No active agent run found for signal target') {
// run already finished or unknown runId — treat as a no-op or recreate context
}
throw e;
} Prevention
- Pass resourceId/threadId explicitly instead of relying on active-run inference
- Treat runIds as ephemeral: don't cache them across long-lived processes
- Use shared pubsub state in distributed setups
- Check run liveness before dispatching signals
When it happens
Trigger: Calling the signal API with only a runId whose record is no longer active (run finished/cleaned up), or with an empty target and no running thread run; race where the run completed between lookup and signal dispatch.
Common situations: Signaling a run after it already finished (async listener fires late); stale runIds cached by the client; signaling on a server instance that doesn't own the run (distributed setups without shared pubsub state).
Related errors
- resourceId and threadId are required to queue a message
- resourceId and threadId are required to send a state signal
- resourceId and threadId are required to persist an active si
- AGENT_SEND_STREAM_RESUME_MISSING_TARGET
- sendStateSignal requires Mastra memory
AI-assisted analysis of mastra-ai/mastra@75dd419e61 (2026-08-30).
Data as JSON: /api/errors/b9e5946b680e2fdf.
Report an issue: GitHub.