aeron-io/aeron · error · AeronException

registration id is not a Subscription

Error message

registration id is not a Subscription: <simpleName>

What it means

Thrown by ClientConductor when removing a subscription by registration id and the id maps to an existing resource that is neither a Subscription nor a PendingSubscription. The conductor keeps resource type checks symmetric with removePublication to prevent releasing the wrong object.

Solutions

  1. Use the registration id from the Subscription (or its future) returned by addSubscription.
  2. Call removePublication/removeCounter for non-subscription ids.
  3. Keep ids in typed wrappers (e.g. record SubscriptionHandle(long regId)) to prevent mix-ups.

Example fix

// before
long id = client.addPublication(channel, streamId).registrationId();
client.removeSubscription(id); // AeronException
// after
long subId = client.addSubscription(channel, streamId).registrationId();
client.removeSubscription(subId);
Defensive patterns

Strategy: try-catch

Validate before calling

if (!(resource instanceof Subscription)) throw new IllegalStateException("id is not a subscription");
client.removeSubscription(subscription.registrationId());

Type guard

boolean isSubscriptionRegId(long regId) { Object r = resourceByRegId(regId); return r instanceof Subscription || r instanceof PendingSubscription; }

Try / catch

try { client.removeSubscription(regId); } catch (AeronException e) { log.warn("reg id {} is not a Subscription: {}", regId, e.getMessage()); }

Prevention

When it happens

Trigger: Calling removeSubscription(subscriptionRegistrationId) with an id belonging to a Publication, Counter, or image-related registration.

Common situations: Storing ids in generic long variables or collections; concurrency refactors that shuffle which id is which; logging/telemetry code echoing the wrong id back into remove calls.

Understand the failure class

Background: Type mismatch errors: IllegalArgumentException, TypeError and type guards across 150 open-source libraries — this error's family across 150 libraries.

Related errors


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

Appendix: source

Thrown at aeron-client/src/main/java/io/aeron/ClientConductor.java:861

        }
    }

    void removeSubscription(final long subscriptionRegistrationId)
    {
        clientLock.lock();
        try
        {
            if (NULL_VALUE == subscriptionRegistrationId || isTerminating || isClosed)
            {
                return;
            }

            ensureNotReentrant();

            final Object resource = resourceByRegIdMap.get(subscriptionRegistrationId);
            if (resource != null && !(resource instanceof PendingSubscription || resource instanceof Subscription))
            {
                throw new AeronException("registration id is not a Subscription: " +
                    resource.getClass().getSimpleName());
            }

            final Subscription subscription = resource instanceof PendingSubscription ?
                ((PendingSubscription)resource).subscription : (Subscription)resource;
            if (null != subscription)
            {
                resourceByRegIdMap.remove(subscriptionRegistrationId);
                subscription.internalClose(EXPLICIT_CLOSE_LINGER_NS);
            }

            if (asyncCommandIdSet.remove(subscriptionRegistrationId) || null != subscription)
            {
                asyncCommandIdSet.add(driverProxy.removeSubscription(subscriptionRegistrationId));
            }
        }
        finally
        {

View on GitHub (pinned to 6d60124e15)