{"record":{"id":"19ccc1435ba5d212","repo":"apache/rocketmq","slug":"long-polling-mode-the-consumer-consumertimeoutmil-19ccc1","errorCode":null,"errorMessage":"Long polling mode, the consumer consumerTimeoutMillisWhenSuspend must greater than brokerSuspendMaxTimeMillis","messagePattern":"Long polling mode, the consumer consumerTimeoutMillisWhenSuspend must greater than brokerSuspendMaxTimeMillis","errorType":"validation","errorClass":"MQClientException","httpStatus":null,"severity":"error","filePath":"client/src/main/java/org/apache/rocketmq/client/impl/consumer/DefaultMQPullConsumerImpl.java","lineNumber":812,"sourceCode":"        // messageModel\n        if (null == this.defaultMQPullConsumer.getMessageModel()) {\n            throw new MQClientException(\n                \"messageModel is null\"\n                    + FAQUrl.suggestTodo(FAQUrl.CLIENT_PARAMETER_CHECK_URL),\n                null);\n        }\n\n        // allocateMessageQueueStrategy\n        if (null == this.defaultMQPullConsumer.getAllocateMessageQueueStrategy()) {\n            throw new MQClientException(\n                \"allocateMessageQueueStrategy is null\"\n                    + FAQUrl.suggestTodo(FAQUrl.CLIENT_PARAMETER_CHECK_URL),\n                null);\n        }\n\n        // allocateMessageQueueStrategy\n        if (this.defaultMQPullConsumer.getConsumerTimeoutMillisWhenSuspend() < this.defaultMQPullConsumer.getBrokerSuspendMaxTimeMillis()) {\n            throw new MQClientException(\n                \"Long polling mode, the consumer consumerTimeoutMillisWhenSuspend must greater than brokerSuspendMaxTimeMillis\"\n                    + FAQUrl.suggestTodo(FAQUrl.CLIENT_PARAMETER_CHECK_URL),\n                null);\n        }\n    }\n\n    private void copySubscription() throws MQClientException {\n        try {\n            Set<String> registerTopics = this.defaultMQPullConsumer.getRegisterTopics();\n            if (registerTopics != null) {\n                for (final String topic : registerTopics) {\n                    SubscriptionData subscriptionData = FilterAPI.buildSubscriptionData(topic, SubscriptionData.SUB_ALL);\n                    this.rebalanceImpl.getSubscriptionInner().put(topic, subscriptionData);\n                }\n            }\n        } catch (Exception e) {\n            throw new MQClientException(\"subscription exception\", e);\n        }","sourceCodeStart":794,"sourceCodeEnd":830,"githubUrl":"https://github.com/apache/rocketmq/blob/293f5885719fc4aa3619446a1900f58ccfcfdd29/client/src/main/java/org/apache/rocketmq/client/impl/consumer/DefaultMQPullConsumerImpl.java#L794-L830","documentation":"Thrown by checkConfig() during start() when consumerTimeoutMillisWhenSuspend < brokerSuspendMaxTimeMillis. In long-polling (blocking) pull mode the broker holds the request up to brokerSuspendMaxTimeMillis; the client must be willing to wait at least that long or every blocked pull would client-side-timeout while the broker is still validly suspended.","triggerScenarios":"Calling consumer.setConsumerTimeoutMillisWhenSuspend(n) or setBrokerSuspendMaxTimeMillis(m) such that n < m before start(); lowering the consumer timeout (e.g. to 5s) while brokerSuspendMaxTimeMillis stays at its default 40s; raising brokerSuspendMaxTimeMillis above the consumer timeout.","commonSituations":"Tuning timeouts to make pulls fail fast without realizing the blocking pull path enforces this invariant; defaults are consistent (consumer timeout 15s vs... in DefaultMQPullConsumer defaults are brokerSuspendMaxTimeMillis=20s and consumerTimeoutMillisWhenSuspend=15s only in push consumer — pull consumer defaults keep the invariant), so this fires after manual tuning.","solutions":["Keep consumerTimeoutMillisWhenSuspend strictly >= brokerSuspendMaxTimeMillis, e.g. broker 20_000 with consumer timeout 25_000","If you want short waits, lower BOTH values together, keeping the invariant","Avoid block=true pulls entirely (use non-blocking pull with a small timeout) if you do not want long polling"],"exampleFix":"// before\nconsumer.setBrokerSuspendMaxTimeMillis(20_000);\nconsumer.setConsumerTimeoutMillisWhenSuspend(5_000); // violates invariant\nconsumer.start();\n\n// after\nconsumer.setBrokerSuspendMaxTimeMillis(20_000);\nconsumer.setConsumerTimeoutMillisWhenSuspend(25_000);\nconsumer.start();","handlingStrategy":"validation","validationCode":"if (consumerTimeoutMillisWhenSuspend < brokerSuspendMaxTimeMillis) {\n    throw new IllegalStateException(\"consumerTimeoutMillisWhenSuspend must be >= brokerSuspendMaxTimeMillis\");\n}","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Keep the invariant timeout >= suspendMax when tuning","Change both timeouts together","Avoid blocking pulls when short waits are required"],"tags":["rocketmq","pull-consumer","long-polling","timeout","config"],"backgroundTag":null,"analyzedSha":"293f5885719fc4aa3619446a1900f58ccfcfdd29","analyzedAt":"2026-08-14T11:50:13.822Z","schemaVersion":2},"datasetVersion":"2026-08-15T17:31:12.345Z"}