aeron-io/aeron · error · ArchiveEvent

ControlSession.RESPONSE_NOT_CONNECTED_MSG + ": " + session

Error message

ControlSession.RESPONSE_NOT_CONNECTED_MSG + ": " + session

What it means

ControlResponseProxy.checkResult throws ArchiveEvent with ControlSession.RESPONSE_NOT_CONNECTED_MSG when sending a control response on the session's publication returns Publication.NOT_CONNECTED. This means the client's control-response image has no active subscriber — the client is no longer connected to the archive's response channel, so the reply cannot be delivered.

Solutions

  1. Treat ArchiveEvent with the not-connected message as a client-gone condition: archive-side code should catch it and clean up the session rather than retry aggressively
  2. On the client, ensure the control-response subscription is established and remains open for the duration of archive requests
  3. Check network connectivity and driver status on the client before/around archive operations
  4. Re-issue the archive request from the client after re-establishing a fresh control session

Example fix

// archive-side handling
try
{
    controlResponseProxy.sendResponse(controlSessionId, correlationId, relevantId, code, message, controlSession);
}
catch (ArchiveEvent e)
{
    if (e.getMessage().startsWith(ControlSession.RESPONSE_NOT_CONNECTED_MSG))
    {
        // client no longer connected; close session instead of retrying
        controlSession.close();
    }
}
Defensive patterns

Strategy: try-catch

Validate before calling

if (aeron.clientVersion() != null && !archiveProxy.isConnected()) { /* reconnect control session before sending requests */ }

Type guard

boolean sessionAlive(ControlSession s) { return s != null && !s.isClosed(); }

Try / catch

try { proxy.sendResponse(...); }
catch (ArchiveEvent e)
{
    if (e.getMessage().startsWith(ControlSession.RESPONSE_NOT_CONNECTED_MSG)) { session.close(); }
    else { throw e; }
}

Prevention

When it happens

Trigger: Calling sendDescriptor, sendResponse, or send on ControlResponseProxy when the underlying control response Publication offers to zero connected subscribers (NOT_CONNECTED), e.g. the client closed its subscription or its media driver went away mid-request.

Common situations: Client application crashed or closed its Aeron connection while a challenge/response or descriptor send was in flight; network/UDP path dropped so the publication has no receivers; client timed out and tore down its subscription while archive still tries to reply.

Understand the failure class

Background: ECONNREFUSED and "connection refused" / "could not connect to server" errors: what they mean and how to fix them — this error's family across 44 libraries.

Related errors


AI-assisted analysis of aeron-io/aeron@6d60124e15 (2026-09-12). Data as JSON: /api/errors/1007b12ab5c7298f. Report an issue: GitHub.

Appendix: source

Thrown at aeron-archive/src/main/java/io/aeron/archive/ControlResponseProxy.java:247

            final long position = session.controlPublication().offer(buffer, 0, length);
            if (position > 0)
            {
                return true;
            }

            checkResult(session, position);
        }
        while (--attempts > 0);

        return false;
    }

    private static void checkResult(final ControlSession session, final long result)
    {
        if (result == Publication.NOT_CONNECTED)
        {
            session.abort(ControlSession.RESPONSE_NOT_CONNECTED_MSG);
            throw new ArchiveEvent(ControlSession.RESPONSE_NOT_CONNECTED_MSG + ": " + session);
        }

        if (result == Publication.CLOSED)
        {
            session.abort("control response publication is closed");
            throw new ArchiveEvent("response publication is closed: " + session, AeronException.Category.ERROR);
        }

        if (result == Publication.MAX_POSITION_EXCEEDED)
        {
            session.abort("control response publication is at max position");
            throw new ArchiveEvent(
                "response publication is at max position: " + session, AeronException.Category.ERROR);
        }
    }

    private void logSendResponse(final DirectBuffer buffer, final int offset, final int length)
    {

View on GitHub (pinned to 6d60124e15)