diff --git a/src/redis.c b/src/redis.c index 5462067a41210909cd98d29c6f90570a22aa8785..8c675b3bdec74661fb2ec11f4815c1abd91bd884 100644 --- a/src/redis.c +++ b/src/redis.c @@ -240,6 +240,7 @@ struct redisCommand redisCommandTable[] = { {"pttl",pttlCommand,2,"r",0,NULL,1,1,1,0,0}, {"persist",persistCommand,2,"w",0,NULL,1,1,1,0,0}, {"slaveof",slaveofCommand,3,"ast",0,NULL,0,0,0,0,0}, + {"role",roleCommand,1,"ast",0,NULL,0,0,0,0,0}, {"debug",debugCommand,-2,"as",0,NULL,0,0,0,0,0}, {"config",configCommand,-2,"art",0,NULL,0,0,0,0,0}, {"subscribe",subscribeCommand,-2,"rpslt",0,NULL,0,0,0,0,0}, diff --git a/src/redis.h b/src/redis.h index 085638a44c615ff5239466c5b232bb0cde450b67..2e176912d1732bc35f525a71b332030a2bc97785 100644 --- a/src/redis.h +++ b/src/redis.h @@ -1300,6 +1300,7 @@ void ttlCommand(redisClient *c); void pttlCommand(redisClient *c); void persistCommand(redisClient *c); void slaveofCommand(redisClient *c); +void roleCommand(redisClient *c); void debugCommand(redisClient *c); void msetCommand(redisClient *c); void msetnxCommand(redisClient *c); diff --git a/src/replication.c b/src/replication.c index ae128b0d98dcf8102396829c294834659a9babd5..4f761698471b2a31f88868b5f311af7701d90db5 100644 --- a/src/replication.c +++ b/src/replication.c @@ -1300,6 +1300,43 @@ void slaveofCommand(redisClient *c) { addReply(c,shared.ok); } +/* ROLE command: provide information about the role of the instance + * (master or slave) and additional information related to replication + * in an easy to process format. */ +void roleCommand(redisClient *c) { + if (server.masterhost == NULL) { + listIter li; + listNode *ln; + void *mbcount; + int slaves = 0; + + addReplyMultiBulkLen(c,3); + addReplyBulkCBuffer(c,"master",6); + addReplyLongLong(c,server.master_repl_offset); + mbcount = addDeferredMultiBulkLength(c); + listRewind(server.slaves,&li); + while((ln = listNext(&li))) { + redisClient *slave = ln->value; + char ip[REDIS_IP_STR_LEN]; + + if (anetPeerToString(slave->fd,ip,sizeof(ip),NULL) == -1) continue; + if (slave->replstate != REDIS_REPL_ONLINE) continue; + addReplyMultiBulkLen(c,3); + addReplyBulkCString(c,ip); + addReplyBulkLongLong(c,slave->slave_listening_port); + addReplyBulkLongLong(c,slave->repl_ack_off); + slaves++; + } + setDeferredMultiBulkLength(c,mbcount,slaves); + } else { + addReplyMultiBulkLen(c,4); + addReplyBulkCBuffer(c,"slave",5); + addReplyBulkCString(c,server.masterhost); + addReplyLongLong(c,server.masterport); + addReplyLongLong(c,server.master->reploff); + } +} + /* Send a REPLCONF ACK command to the master to inform it about the current * processed offset. If we are not connected with a master, the command has * no effects. */