Netflix/Hystrix · error · HystrixRuntimeException

" + getLogMessagePrefix() + " command executed multiple time

Error message

" + getLogMessagePrefix() + " command executed multiple times - this is not permitted.

What it means

A HystrixCommand/HystrixObservableCommand instance is a stateful object that may be executed only once; the constructor-to-execution chain guards this with commandState.compareAndSet(NOT_STARTED, OBSERVABLE_CHAIN_CREATED). Calling execute(), queue(), observe(), or toObservable() again on the same instance throws HystrixRuntimeException (typed BAD_REQUEST_EXCEPTION) with 'command executed multiple times - this is not permitted'.

Source

Thrown at hystrix-core/src/main/java/com/netflix/hystrix/AbstractCommand.java:462

        final Action0 fireOnCompletedHook = new Action0() {
            @Override
            public void call() {
                try {
                    executionHook.onSuccess(_cmd);
                } catch (Throwable hookEx) {
                    logger.warn("Error calling HystrixCommandExecutionHook.onSuccess", hookEx);
                }
            }
        };

        return Observable.defer(new Func0<Observable<R>>() {
            @Override
            public Observable<R> call() {
                 /* this is a stateful object so can only be used once */
                if (!commandState.compareAndSet(CommandState.NOT_STARTED, CommandState.OBSERVABLE_CHAIN_CREATED)) {
                    IllegalStateException ex = new IllegalStateException("This instance can only be executed once. Please instantiate a new instance.");
                    //TODO make a new error type for this
                    throw new HystrixRuntimeException(FailureType.BAD_REQUEST_EXCEPTION, _cmd.getClass(), getLogMessagePrefix() + " command executed multiple times - this is not permitted.", ex, null);
                }

                commandStartTimestamp = System.currentTimeMillis();

                if (properties.requestLogEnabled().get()) {
                    // log this command execution regardless of what happened
                    if (currentRequestLog != null) {
                        currentRequestLog.addExecutedCommand(_cmd);
                    }
                }

                final boolean requestCacheEnabled = isRequestCachingEnabled();
                final String cacheKey = getCacheKey();

                /* try from cache first */
                if (requestCacheEnabled) {
                    HystrixCommandResponseFromCache<R> fromCache = (HystrixCommandResponseFromCache<R>) requestCache.get(cacheKey);
                    if (fromCache != null) {

View on GitHub (pinned to 5ce3bc58c3)

Solutions

  1. Instantiate a fresh command instance for every execution (move construction inside the method/lambda that runs it)
  2. For retries, create a new command per attempt (e.g. in a Observable.defer or a loop factory)
  3. Never store commands in long-lived fields of singletons; store the parameters instead and build the command on demand
  4. Catch HystrixRuntimeException and check getFailureType()==BAD_REQUEST_EXCEPTION to detect reuse bugs early in tests

Example fix

// before
class Service { private final HystrixCommand<String> cmd = new MyCommand(); 
  String call() { return cmd.execute(); } } // fails on 2nd call
// after
class Service {
  String call() { return new MyCommand().execute(); } }
Defensive patterns

Strategy: validation

Validate before calling

// construct a fresh instance per call — nothing to validate at runtime beyond not reusing the instance
if (commandWasAlreadyUsed) throw new IllegalStateException("create a new command instance");

Type guard

null

Try / catch

catch (HystrixRuntimeException e) { if (e.getFailureType() == FailureType.BAD_REQUEST_EXCEPTION && e.getMessage().contains("executed multiple times")) { // reuse bug — create new instance and retry once with a NEW command } }

Prevention

When it happens

Trigger: Calling command.execute() a second time; mixing execute() then toObservable() on the same instance; caching command instances (fields, collections, request-scoped beans) and reusing them across requests; subscribing twice to the Observable returned by a single instance.

Common situations: Spring singleton beans holding a HystrixCommand field; retry loops that re-run the same command object; accidentally putting commands in a map keyed by cache key; toObservable() invoked in both a doOnSubscribe hook and by the caller.

Related errors


AI-assisted analysis of Netflix/Hystrix@5ce3bc58c3 (2026-08-14). Data as JSON: /api/errors/31b658e2ee9f69e7. Report an issue: GitHub.