{"record":{"id":"ac0341ed16bc90f7","repo":"redis/jedis","slug":"cluster-retry-deadline-exceeded","errorCode":null,"errorMessage":"Cluster retry deadline exceeded.","messagePattern":"Cluster retry deadline exceeded\\.","errorType":"exception","errorClass":"JedisClusterOperationException","httpStatus":null,"severity":"critical","filePath":"src/main/java/redis/clients/jedis/executors/ClusterCommandExecutor.java","lineNumber":300,"sourceCode":"        if (followRedirections) {\n          log.debug(\"Redirected by server to {}\", jre.getTargetNode());\n          redirect = jre;\n          // if MOVED redirection occurred,\n          if (jre instanceof JedisMovedDataException) {\n            // it rebuilds cluster's slot cache recommended by Redis cluster specification\n            provider.renewSlotCache(connection);\n          }\n        } else {\n          // When followRedirections is false, throw the redirection exception immediately\n          // instead of silently handling or ignoring it\n          throw jre;\n        }\n        consecutiveConnectionFailures = 0;\n      } finally {\n        IOUtils.closeQuietly(connection);\n      }\n      if (Instant.now().isAfter(deadline)) {\n        throw new JedisClusterOperationException(\"Cluster retry deadline exceeded.\", lastException,\n            lastNode);\n      }\n    }\n\n    JedisClusterOperationException maxAttemptsException =\n        new JedisClusterOperationException(\"No more cluster attempts left.\", lastException,\n            lastNode);\n    throw maxAttemptsException;\n  }\n\n    /**\n   * WARNING: This method is accessible for the purpose of testing.\n   * This should not be used or overriden.\n   */\n  @VisibleForTesting\n  protected <T> T execute(Connection connection, CommandObject<T> commandObject) {\n    return connection.executeCommand(commandObject);\n  }","sourceCodeStart":282,"sourceCodeEnd":318,"githubUrl":"https://github.com/redis/jedis/blob/6dac31d4c224fb3257c216f3985340c6f500cdcb/src/main/java/redis/clients/jedis/executors/ClusterCommandExecutor.java#L282-L318","documentation":"During command execution the ClusterCommandExecutor retries failed commands against cluster nodes until an attempt/deadline budget is exhausted. When the wall-clock retry deadline passes, it throws JedisClusterOperationException(\"Cluster retry deadline exceeded.\") carrying the last underlying exception and last node as cause/suppressed context. It means the command could not be completed within the configured timeout despite retries.","triggerScenarios":"Persistent connection failures to cluster nodes (MOVED/ASK loops, node down), Redis server unresponsive or network partitioned, while cluster-configured maxAttempts and the deadline elapse inside doExecuteCommand.","commonSituations":"Redis cluster node down or being failed over; network partition between client and cluster; cluster state degraded (slot not covered); severe latency making each attempt slow so the deadline expires after only a few retries.","solutions":["Inspect the cause/suppressed JedisConnectionException and lastNode to find the failing node; verify cluster node health with `redis-cli cluster info` / `cluster nodes`.","Increase the retry deadline/maxAttempts in the cluster client configuration if your workload tolerates longer waits.","Restore connectivity: restart failed nodes, fix firewall/security-group rules, and confirm slots are fully covered (no 16384-slot gaps).","Reduce per-attempt timeouts so more attempts fit within the deadline instead of one slow attempt consuming it."],"exampleFix":"// before\nRedisClusterClient.create(\"127.0.0.1:7000\")\n    .build();\n// after\nRedisClusterClient.create(\"127.0.0.1:7000\")\n    .socketTimeout(Duration.ofSeconds(2))   // shorter per-attempt timeout\n    .maxAttempts(20)                        // more retry budget\n    .build();","handlingStrategy":"try-catch","validationCode":"// verify cluster reachability before issuing commands\ntry (Jedis j = new Jedis(anyStartupNode)) {\n  String state = j.clusterInfo();\n  if (!state.contains(\"cluster_state:ok\")) throw new IllegalStateException(\"cluster degraded\");\n}","typeGuard":null,"tryCatchPattern":"try {\n  return cluster.get(key);\n} catch (JedisClusterOperationException e) {\n  Throwable cause = e.getCause();\n  logger.error(\"deadline exceeded on node {} : {}\", e.getLastNode(), cause, e);\n  throw new ServiceUnavailableException(e);\n}","preventionTips":["Monitor cluster health (cluster_state, node failures) with alerts","Set per-attempt timeouts well below the retry deadline","Size maxAttempts to the deadline so attempts aren't truncated","Use multiple startup nodes from different availability zones"],"tags":["cluster","retry","timeout","network","failover"],"backgroundTag":"request-timeout","analyzedSha":"6dac31d4c224fb3257c216f3985340c6f500cdcb","analyzedAt":"2026-09-08T04:55:01.204Z","contentChangedAt":"2026-09-08T04:55:01.204Z","schemaVersion":2},"datasetVersion":"2026-09-16T04:17:20.429Z"}