mirror of
https://github.com/fluencelabs/redis
synced 2025-03-17 16:10:50 +00:00
Cluster: nodes re-addition blacklist API.
This commit is contained in:
parent
8f18345ef0
commit
6fa42b7507
@ -622,6 +622,75 @@ void clusterRenameNode(clusterNode *node, char *newname) {
|
||||
clusterAddNode(node);
|
||||
}
|
||||
|
||||
/* -----------------------------------------------------------------------------
|
||||
* CLUSTER nodes blacklist
|
||||
*
|
||||
* The nodes blacklist is just a way to ensure that a given node with a given
|
||||
* Node ID is not readded before some time elapsed (this time is specified
|
||||
* in seconds in REDIS_CLUSTER_BLACKLIST_TTL).
|
||||
*
|
||||
* This is useful when we want to remove a node from the cluster completely:
|
||||
* when CLUSTER FORGET is called, it also puts the node into the blacklist so
|
||||
* that even if we receive gossip messages from other nodes that still remember
|
||||
* about the node we want to remove, we don't re-add it before some time.
|
||||
*
|
||||
* Currently the REDIS_CLUSTER_BLACKLIST_TTL is set to 1 minute, this means
|
||||
* that redis-trib has 60 seconds to send CLUSTER FORGET messages to nodes
|
||||
* in the cluster without dealing with the problem if other nodes re-adding
|
||||
* back the node to nodes we already sent the FORGET command to.
|
||||
*
|
||||
* The data structure used is an hash table with an sds string representing
|
||||
* the node ID as key, and the time when it is ok to re-add the node as
|
||||
* value.
|
||||
* -------------------------------------------------------------------------- */
|
||||
|
||||
#define REDIS_CLUSTER_BLACKLIST_TTL 60 /* 1 minute. */
|
||||
|
||||
|
||||
/* Before of the addNode() or Exists() operations we always remove expired
|
||||
* entries from the black list. This is an O(N) operation but it is not a
|
||||
* problem since add / exists operations are called very infrequently and
|
||||
* the hash table is supposed to contain very little elements at max.
|
||||
* However without the cleanup during long uptimes and with some automated
|
||||
* node add/removal procedures, entries could accumulate. */
|
||||
void clusterBlacklistCleanup(void) {
|
||||
dictIterator *di;
|
||||
dictEntry *de;
|
||||
|
||||
di = dictGetSafeIterator(server.cluster->nodes_black_list);
|
||||
while((de = dictNext(di)) != NULL) {
|
||||
int64_t expire = dictGetUnsignedIntegerVal(de);
|
||||
|
||||
if (expire < server.unixtime)
|
||||
dictDelete(server.cluster->nodes_black_list,dictGetKey(de));
|
||||
}
|
||||
dictReleaseIterator(di);
|
||||
}
|
||||
|
||||
/* Cleanup the blacklist and add a new node ID to the black list. */
|
||||
void clusterBlacklistAddNode(clusterNode *node) {
|
||||
dictEntry *de;
|
||||
sds id = sdsnewlen(node->name,REDIS_CLUSTER_NAMELEN);
|
||||
|
||||
clusterBlacklistCleanup();
|
||||
if (dictAdd(server.cluster->nodes_black_list,id,NULL) == DICT_ERR)
|
||||
sdsfree(id); /* Key was already there. */
|
||||
de = dictFind(server.cluster->nodes_black_list,node->name);
|
||||
dictSetUnsignedIntegerVal(de,time(NULL));
|
||||
}
|
||||
|
||||
/* Return non-zero if the specified node ID exists in the blacklist.
|
||||
* You don't need to pass an sds string here, any pointer to 40 bytes
|
||||
* will work. */
|
||||
int clusterBlacklistExists(char *nodeid) {
|
||||
sds id = sdsnewlen(nodeid,REDIS_CLUSTER_NAMELEN);
|
||||
int retval;
|
||||
|
||||
retval = dictFind(server.cluster->nodes_black_list,id) != NULL;
|
||||
sdsfree(id);
|
||||
return retval;
|
||||
}
|
||||
|
||||
/* -----------------------------------------------------------------------------
|
||||
* CLUSTER messages exchange - PING/PONG and gossip
|
||||
* -------------------------------------------------------------------------- */
|
||||
|
Loading…
x
Reference in New Issue
Block a user