summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorantirez <antirez@gmail.com>2010-11-04 19:59:21 +0100
committerantirez <antirez@gmail.com>2010-11-04 19:59:21 +0100
commit4ebfc45528dea7a3b0e4bc2a8efd4238ea48347b (patch)
tree957924fce0efa7abeff36c06fb27729eee07e73c /src
parent12ebe2ac17a26ecf263f90b2acdf03db29b00223 (diff)
downloadredis-4ebfc45528dea7a3b0e4bc2a8efd4238ea48347b.tar.gz
config option to select if when replication link with master a slave should or not serve stale data
Diffstat (limited to 'src')
-rw-r--r--src/config.c14
-rw-r--r--src/redis.c12
-rw-r--r--src/redis.h4
3 files changed, 29 insertions, 1 deletions
diff --git a/src/config.c b/src/config.c
index 2b5063c8f..772ac764e 100644
--- a/src/config.c
+++ b/src/config.c
@@ -152,6 +152,10 @@ void loadServerConfig(char *filename) {
server.replstate = REDIS_REPL_CONNECT;
} else if (!strcasecmp(argv[0],"masterauth") && argc == 2) {
server.masterauth = zstrdup(argv[1]);
+ } else if (!strcasecmp(argv[0],"slave-serve-stale-data") && argc == 2) {
+ if ((server.repl_serve_stale_data = yesnotoi(argv[1])) == -1) {
+ err = "argument must be 'yes' or 'no'"; goto loaderr;
+ }
} else if (!strcasecmp(argv[0],"glueoutputbuf") && argc == 2) {
if ((server.glueoutputbuf = yesnotoi(argv[1])) == -1) {
err = "argument must be 'yes' or 'no'"; goto loaderr;
@@ -379,6 +383,11 @@ void configSetCommand(redisClient *c) {
appendServerSaveParams(seconds, changes);
}
sdsfreesplitres(v,vlen);
+ } else if (!strcasecmp(c->argv[2]->ptr,"slave-serve-stale-data")) {
+ int yn = yesnotoi(o->ptr);
+
+ if (yn == -1) goto badfmt;
+ server.repl_serve_stale_data = yn;
} else {
addReplyErrorFormat(c,"Unsupported CONFIG parameter: %s",
(char*)c->argv[2]->ptr);
@@ -488,6 +497,11 @@ void configGetCommand(redisClient *c) {
sdsfree(buf);
matches++;
}
+ if (stringmatch(pattern,"slave-serve-stale-data",0)) {
+ addReplyBulkCString(c,"slave-serve-stale-data");
+ addReplyBulkCString(c,server.repl_serve_stale_data ? "yes" : "no");
+ matches++;
+ }
setDeferredMultiBulkLength(c,replylen,matches*2);
}
diff --git a/src/redis.c b/src/redis.c
index 971dfecad..8519f46ff 100644
--- a/src/redis.c
+++ b/src/redis.c
@@ -786,6 +786,7 @@ void initServerConfig() {
server.masterport = 6379;
server.master = NULL;
server.replstate = REDIS_REPL_NONE;
+ server.repl_serve_stale_data = 1;
/* Double constants initialization */
R_Zero = 0.0;
@@ -994,6 +995,17 @@ int processCommand(redisClient *c) {
return REDIS_OK;
}
+ /* Only allow INFO and SLAVEOF when slave-serve-stale-data is no and
+ * we are a slave with a broken link with master. */
+ if (server.masterhost && server.replstate != REDIS_REPL_CONNECTED &&
+ server.repl_serve_stale_data == 0 &&
+ cmd->proc != infoCommand && cmd->proc != slaveofCommand)
+ {
+ addReplyError(c,
+ "link with MASTER is down and slave-serve-stale-data is set to no");
+ return REDIS_OK;
+ }
+
/* Exec the command */
if (c->flags & REDIS_MULTI &&
cmd->proc != execCommand && cmd->proc != discardCommand &&
diff --git a/src/redis.h b/src/redis.h
index d26e3c797..043825af7 100644
--- a/src/redis.h
+++ b/src/redis.h
@@ -361,7 +361,8 @@ struct redisServer {
long long dirty_before_bgsave; /* used to restore dirty on failed BGSAVE */
list *clients;
dict *commands; /* Command table hahs table */
- struct redisCommand *delCommand, *multiCommand; /* often lookedup cmds */
+ /* Fast pointers to often looked up command */
+ struct redisCommand *delCommand, *multiCommand;
list *slaves, *monitors;
char neterr[ANET_ERR_LEN];
aeEventLoop *el;
@@ -413,6 +414,7 @@ struct redisServer {
int repl_transfer_fd; /* slave -> master SYNC temp file descriptor */
char *repl_transfer_tmpfile; /* slave-> master SYNC temp file name */
time_t repl_transfer_lastio; /* unix time of the latest read, for timeout */
+ int repl_serve_stale_data; /* Serve stale data when link is down? */
/* Limits */
unsigned int maxclients;
unsigned long long maxmemory;