mirror of
https://github.com/fluencelabs/redis
synced 2025-03-17 16:10:50 +00:00
CLUSTER SLOTS: don't output failing slaves.
While we have to output failing masters in order to provide an accurate map (that may be the one of a Redis Cluster in down state because not all slots are served by a working master), to provide slaves in FAIL state is not a good idea since those are not necesarely needed, and the client will likely incur into a latency penalty trying to connect with a slave which is down. Note that this means that CLUSTER SLOTS does not provide a *complete* map of slaves, however this would not be of any help since slaves may be added later, and a client that needs to scale reads and requires to stay updated with the list of slaves, need to do a refresh of the map from time to time, anyway.
This commit is contained in:
parent
a6fe4ca321
commit
75c57d53ea
@ -3458,8 +3458,8 @@ void clusterReplyMultiBulkSlots(redisClient *c) {
|
||||
* ... continued until done
|
||||
*/
|
||||
|
||||
int repliedRangeCount = 0;
|
||||
void *slotreplylen = addDeferredMultiBulkLength(c);
|
||||
int num_masters = 0;
|
||||
void *slot_replylen = addDeferredMultiBulkLength(c);
|
||||
|
||||
dictEntry *de;
|
||||
dictIterator *di = dictGetSafeIterator(server.cluster->nodes);
|
||||
@ -3472,16 +3472,16 @@ void clusterReplyMultiBulkSlots(redisClient *c) {
|
||||
if (!nodeIsMaster(node) || node->numslots == 0) continue;
|
||||
|
||||
for (j = 0; j < REDIS_CLUSTER_SLOTS; j++) {
|
||||
int bit;
|
||||
int bit, i;
|
||||
|
||||
if ((bit = clusterNodeGetSlotBit(node,j)) != 0) {
|
||||
if (start == -1) start = j;
|
||||
}
|
||||
if (start != -1 && (!bit || j == REDIS_CLUSTER_SLOTS-1)) {
|
||||
if (bit && j == REDIS_CLUSTER_SLOTS-1) j++;
|
||||
int nested_elements = 3; /* slots (2) + master addr (1). */
|
||||
void *nested_replylen = addDeferredMultiBulkLength(c);
|
||||
|
||||
/* nested size: slots (2) + master (1) + slaves */
|
||||
addReplyMultiBulkLen(c, 2 + 1 + node->numslaves);
|
||||
if (bit && j == REDIS_CLUSTER_SLOTS-1) j++;
|
||||
|
||||
/* If slot exists in output map, add to it's list.
|
||||
* else, create a new output map for this slot */
|
||||
@ -3500,20 +3500,22 @@ void clusterReplyMultiBulkSlots(redisClient *c) {
|
||||
addReplyLongLong(c, node->port);
|
||||
|
||||
/* Remaining nodes in reply are replicas for slot range */
|
||||
int i;
|
||||
for (i = 0; i < node->numslaves; i++) {
|
||||
/* This loop is copy/pasted from clusterGenNodeDescription()
|
||||
* with modifications for per-slot node aggregation */
|
||||
if (nodeFailed(node->slaves[i])) continue;
|
||||
addReplyMultiBulkLen(c, 2);
|
||||
addReplyBulkCString(c, node->slaves[i]->ip);
|
||||
addReplyLongLong(c, node->slaves[i]->port);
|
||||
nested_elements++;
|
||||
}
|
||||
repliedRangeCount++;
|
||||
setDeferredMultiBulkLength(c, nested_replylen, nested_elements);
|
||||
num_masters++;
|
||||
}
|
||||
}
|
||||
}
|
||||
dictReleaseIterator(di);
|
||||
setDeferredMultiBulkLength(c, slotreplylen, repliedRangeCount);
|
||||
setDeferredMultiBulkLength(c, slot_replylen, num_masters);
|
||||
}
|
||||
|
||||
void clusterCommand(redisClient *c) {
|
||||
|
Loading…
x
Reference in New Issue
Block a user