dotnet/aspnetcore · error · IllegalStateException
Invocation Id is already used
Error message
Invocation Id is already used
What it means
An IllegalStateException thrown by ConnectionState.addInvocation when an InvocationRequest with the same invocationId already exists in pendingInvocations. Invocation IDs are generated monotonically via AtomicInteger (getNextInvocationId), so a duplicate under normal single-connection usage is an internal invariant violation indicating the ID generator wrapped or state corrupted.
Source
Thrown at src/SignalR/clients/java/signalr/core/src/main/java/com/microsoft/signalr/HubConnection.java:1437
for (String key : keys) {
if (ex == null) {
pendingInvocations.get(key).cancel();
} else {
pendingInvocations.get(key).fail(ex);
}
}
pendingInvocations.clear();
} finally {
lock.unlock();
}
}
public void addInvocation(InvocationRequest irq) {
lock.lock();
try {
if (pendingInvocations.containsKey(irq.getInvocationId())) {
throw new IllegalStateException("Invocation Id is already used");
} else {
pendingInvocations.put(irq.getInvocationId(), irq);
}
} finally {
lock.unlock();
}
}
public InvocationRequest getInvocation(String id) {
lock.lock();
try {
return pendingInvocations.get(id);
} finally {
lock.unlock();
}
}
public InvocationRequest tryRemoveInvocation(String id) {View on GitHub (pinned to 294cab2f9b)
Solutions
- If reproduced in test code, stop manually setting invocation IDs; let getNextInvocationId generate them.
- In production, this indicates a library-level issue; report with a repro and the connection lifecycle trace.
- Restart the HubConnection (stop + start) to reset the ID counter and clear pendingInvocations.
Example fix
// before (test): manual duplicate id String id = "1"; connectionState.addInvocation(new InvocationRequest(null, id)); connectionState.addInvocation(new InvocationRequest(null, id)); // throws // after: let the connection generate unique ids String id = connectionState.getNextInvocationId(); connectionState.addInvocation(new InvocationRequest(null, id));
Defensive patterns
Strategy: try-catch
Validate before calling
// No public pre-check; this is an internal invariant. The practical guard is to never
// manually inject invocation IDs and to restart the connection if it occurs.
if (connection.getConnectionState() != HubConnectionState.CONNECTED) {
// don't invoke; avoids internal state corruption
} Try / catch
try {
connection.invoke("method").blockingAwait();
} catch (IllegalStateException e) {
if (e.getMessage().contains("Invocation Id is already used")) {
// internal ID collision; restart the connection to reset state
connection.stop().blockingAwait();
connection.start().blockingAwait();
} else { throw e; }
} Prevention
- Never manually construct InvocationRequest with hardcoded IDs in production code.
- If the error recurs, restart the HubConnection to reset the ID counter.
- Report persistent reproduction as a library bug with a connection lifecycle trace.
When it happens
Trigger: addInvocation(irq) is called with an id already present in pendingInvocations. In practice this requires the nextId AtomicInteger to produce a value that collides with a still-pending request, which should not happen in correct single-connection operation. Could be triggered by manual id injection in tests or by reusing a HubConnection's internal ConnectionState across logical connections.
Common situations: Test code that manually constructs InvocationRequest objects and calls addInvocation with hardcoded ids. A long-lived connection whose integer ID counter is theoretically approaching limits (unlikely). Concurrent invoke/stream calls racing through getNextInvocationId in a way that, combined with a bug, reuses an id. Generally an internal/library bug if seen in production.
Related errors
- HubConnection trying to negotiate when not in the CONNECTING
- Trying to send and message while the connection is not activ
- Connection is not active.
- The HubConnection failed to transition from the '%s' state t
- Invocation provides %d argument(s) but target expects %d.
AI-assisted analysis of dotnet/aspnetcore@294cab2f9b (2026-08-06).
Data as JSON: /api/errors/388d46be9d13dcb2.
Report an issue: GitHub.