apache/incubator-seata · error · FrameworkException

timeout should more than 0ms

Error message

timeout should more than 0ms

What it means

AbstractNettyRemoting.sendSync guards the RPC timeout up front: a timeoutMillis of 0 or less cannot block meaningfully on the MessageFuture, so it fails fast with FrameworkException instead of hanging or busy-waiting. The value typically originates from RPC timeout config (tm/rm rpc timeout, or per-request timeouts derived from config).

Source

Thrown at core/src/main/java/org/apache/seata/core/rpc/netty/AbstractNettyRemoting.java:187

    @Override
    public void destroy() {
        timerExecutor.shutdown();
        messageExecutor.shutdown();
    }

    /**
     * rpc sync request
     * Obtain the return result through MessageFuture blocking.
     *
     * @param channel       netty channel
     * @param rpcMessage    rpc message
     * @param timeoutMillis rpc communication timeout
     * @return response message
     * @throws TimeoutException
     */
    protected Object sendSync(Channel channel, RpcMessage rpcMessage, long timeoutMillis) throws TimeoutException {
        if (timeoutMillis <= 0) {
            throw new FrameworkException("timeout should more than 0ms");
        }
        if (channel == null) {
            LOGGER.warn("sendSync nothing, caused by null channel.");
            return null;
        }
        if (MsgVersionHelper.versionNotSupport(channel, rpcMessage)) {
            if (LOGGER.isDebugEnabled()) {
                LOGGER.debug(
                        "Message sending will be skipped as the client version does not support it,{}", rpcMessage);
            }
            return new VersionNotSupportMessage();
        }

        MessageFuture messageFuture = new MessageFuture();
        messageFuture.setRequestMessage(rpcMessage);
        messageFuture.setTimeout(timeoutMillis);
        futures.put(rpcMessage.getId(), messageFuture);

View on GitHub (pinned to e01f97c6db)

Solutions

  1. Set a positive timeout in milliseconds (e.g. 30000) in the client tm/rm RPC timeout configuration.
  2. Fix unit math at call sites: ensure milliseconds are passed, and clamp computed timeouts to a minimum of 1.
  3. If you intended 'no timeout', use async send instead of sendSync — there is no infinite sync wait.

Example fix

# before
seata.client.tm.rpc-timeout=0
# after
seata.client.tm.rpc-timeout=30000
Defensive patterns

Strategy: validation

Validate before calling

long safeTimeout(long ms) { return Math.max(ms, 1_000); }
long t = safeTimeout(configuredTimeout); // reject 0/negative before sendSync

Type guard

boolean usableTimeout(long ms) { return ms > 0; }

Try / catch

catch (FrameworkException e) {
    if (e.getMessage().contains("timeout should more than 0ms")) { fixConfigThenRetry(defaultTimeout); }
    else throw e;
}

Prevention

When it happens

Trigger: Invoking a sync request with a computed timeout that is <=0 — config set to 0, a unit-conversion bug (seconds vs ms), or code computing timeout = deadline - now after the deadline already passed.

Common situations: seata client rpc timeout configured as 0 (misread as 'infinite'), custom DeadlineRunner code subtracting elapsed time and passing a negative remainder, or copying timeouts from another system expressed in seconds into a millisecond API.

Understand the failure class

Related errors


AI-assisted analysis of apache/incubator-seata@e01f97c6db (2026-08-14). Data as JSON: /api/errors/bce9c39fcd59a7b6. Report an issue: GitHub.