From 2f6ed9333f082b9cd27bfab05013521b88f077c7 Mon Sep 17 00:00:00 2001 From: Angus Pearson Date: Wed, 2 Jan 2019 18:50:58 +0000 Subject: [PATCH 1/2] Fix broken interval and repeat bahaviour in redis-cli (incluing cluster mode) This addresses two problems, one where infinite (negative) repeat count is broken for all types for Redis, and another specific to cluster mode where redirection is needed. Now allows and works correctly for negative (i.e. -1) repeat values passed with `-r` argument to redis-cli as documented here https://redis.io/topics/rediscli#continuously-run-the-same-command which seems to have regressed as a feature in 95b988 (though that commit removed bad integer wrap-around to `0` behaviour). This broken behaviour exists currently (e50458), and redis-cli will just exit immediately with repeat `-r <= 0` as opposed to send commands indefinitely as it should with `-r < 0` Additionally prevents a repeat * interval seconds hang/time spent doing nothing at the start before issuing commands in cluster mode (`-c`), where the command needed to redirect to a slot on another node, as commands where failing and waiting to be reissued but this was fully repeated before being reissued. For example, redis-cli -c -r 10 -i 0.5 INCR test_key_not_on_6379 Would hang and show nothing for 5 seconds (10 * 0.5) before showing (integer) 1 (integer) 2 (integer) 3 (integer) 4 (integer) 5 (integer) 6 (integer) 7 (integer) 8 (integer) 9 (integer) 10 at half second intervals as intended. --- src/redis-cli.c | 17 +++++++++++------ 1 file changed, 11 insertions(+), 6 deletions(-) diff --git a/src/redis-cli.c b/src/redis-cli.c index 6fe93e66..d9145454 100644 --- a/src/redis-cli.c +++ b/src/redis-cli.c @@ -1141,7 +1141,7 @@ static int cliSendCommand(int argc, char **argv, long repeat) { for (j = 0; j < argc; j++) argvlen[j] = sdslen(argv[j]); - while(repeat-- > 0) { + while(repeat < 0 || repeat-- > 0) { redisAppendCommandArgv(context,argc,(const char**)argv,argvlen); while (config.monitor_mode) { if (cliReadReply(output_raw) != REDIS_OK) exit(1); @@ -1176,6 +1176,11 @@ static int cliSendCommand(int argc, char **argv, long repeat) { cliSelect(); } } + if (config.cluster_reissue_command){ + /* If we need to reissue the command, break to prevent a + further 'repeat' number of dud interations */ + break; + } if (config.interval) usleep(config.interval); fflush(stdout); /* Make it grep friendly */ } @@ -1569,12 +1574,12 @@ static int issueCommandRepeat(int argc, char **argv, long repeat) { cliPrintContextError(); return REDIS_ERR; } - } - /* Issue the command again if we got redirected in cluster mode */ - if (config.cluster_mode && config.cluster_reissue_command) { + } + /* Issue the command again if we got redirected in cluster mode */ + if (config.cluster_mode && config.cluster_reissue_command) { cliConnect(CC_FORCE); - } else { - break; + } else { + break; } } return REDIS_OK; From 2925bdc63bcf62acd8a536cc629f4a54d64b370c Mon Sep 17 00:00:00 2001 From: Angus Pearson Date: Wed, 2 Jan 2019 19:21:49 +0000 Subject: [PATCH 2/2] Add comment explaining negative repeat --- src/redis-cli.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/redis-cli.c b/src/redis-cli.c index d9145454..5ff0ad1d 100644 --- a/src/redis-cli.c +++ b/src/redis-cli.c @@ -1141,6 +1141,8 @@ static int cliSendCommand(int argc, char **argv, long repeat) { for (j = 0; j < argc; j++) argvlen[j] = sdslen(argv[j]); + /* Negative repeat is allowed and causes infinite loop, + works well with the interval option. */ while(repeat < 0 || repeat-- > 0) { redisAppendCommandArgv(context,argc,(const char**)argv,argvlen); while (config.monitor_mode) {