quarkusio/quarkus · error · IllegalArgumentException

Invalid state: " + state.getClass().getName()

Error message

Invalid state: " + state.getClass().getName()

What it means

AbstractSharedContext.destroy(ContextState) throws IllegalArgumentException when the given state is not the context itself. A shared context only accepts destroying its own state (self-destruction) or states it owns; a foreign ContextState indicates a programming error by the caller.

Source

Thrown at independent-projects/arc/runtime/src/main/java/io/quarkus/arc/impl/AbstractSharedContext.java:133

                    instanceHandle.destroy();
                }
            });
        }
        instances.removeEach(null);
    }

    private ArcShutdownAction actionType(InjectableBean<?> bean) {
        return bean.getScope().equals(ApplicationScoped.class)
                ? ArcShutdownAction.CDI_DESTROY_APPLICATION_BEAN
                : ArcShutdownAction.CDI_DESTROY_SINGLETON_BEAN;
    }

    @Override
    public void destroy(ContextState state) {
        if (state == this) {
            destroy();
        } else {
            throw new IllegalArgumentException("Invalid state: " + state.getClass().getName());
        }
    }

    @SuppressWarnings({ "unchecked", "rawtypes" })
    private static <T> ContextInstanceHandle createInstanceHandle(InjectableBean<T> bean,
            CreationalContext<T> creationalContext) {
        return new ContextInstanceHandleImpl(bean, bean.create(creationalContext), creationalContext);
    }

}

View on GitHub (pinned to e1c734241f)

Solutions

  1. Call context.destroy() (no args) to destroy the context's current state instead of passing an external state
  2. Only pass ContextState values obtained from this same context instance
  3. Guard with context.getState() == state before calling destroy(state)
  4. Re-create the handle/context pair if states were obtained from a previous container instance

Example fix

// before
appContext.destroy(someOtherState); // IllegalArgumentException
// after
if (appContext.getState() == someState) {
    appContext.destroy(someState);
} else {
    appContext.destroy();
}
Defensive patterns

Strategy: type-guard

Validate before calling

if (ctx.getState() != state) { ctx.destroy(); return; }

Type guard

boolean owned = state != null && ctx.getState() == state;

Try / catch

try { ctx.destroy(state); } catch (IllegalArgumentException e) { ctx.destroy(); }

Prevention

When it happens

Trigger: Calling context.destroy(someState) with a ContextState obtained from a different context instance (e.g. two @ApplicationScoped contexts, or a state from a mock/custom context).

Common situations: Custom context implementations mismanaging state ownership; tests reusing ContextState across container restarts; multiple containers (dev mode restarts) mixing stale states with fresh contexts.

Related errors


AI-assisted analysis of quarkusio/quarkus@e1c734241f (2026-09-05). Data as JSON: /api/errors/c5c6324ccce352bc. Report an issue: GitHub.