2019-10-03 07:06:09 -04:00
|
|
|
/* This module is used to test the propagation (replication + AOF) of
|
|
|
|
* commands, via the RedisModule_Replicate() interface, in asynchronous
|
|
|
|
* contexts, such as callbacks not implementing commands, and thread safe
|
|
|
|
* contexts.
|
|
|
|
*
|
|
|
|
* We create a timer callback and a threads using a thread safe context.
|
|
|
|
* Using both we try to propagate counters increments, and later we check
|
|
|
|
* if the replica contains the changes as expected.
|
|
|
|
*
|
|
|
|
* -----------------------------------------------------------------------------
|
|
|
|
*
|
|
|
|
* Copyright (c) 2019, Salvatore Sanfilippo <antirez at gmail dot com>
|
|
|
|
* All rights reserved.
|
|
|
|
*
|
|
|
|
* Redistribution and use in source and binary forms, with or without
|
|
|
|
* modification, are permitted provided that the following conditions are met:
|
|
|
|
*
|
|
|
|
* * Redistributions of source code must retain the above copyright notice,
|
|
|
|
* this list of conditions and the following disclaimer.
|
|
|
|
* * Redistributions in binary form must reproduce the above copyright
|
|
|
|
* notice, this list of conditions and the following disclaimer in the
|
|
|
|
* documentation and/or other materials provided with the distribution.
|
|
|
|
* * Neither the name of Redis nor the names of its contributors may be used
|
|
|
|
* to endorse or promote products derived from this software without
|
|
|
|
* specific prior written permission.
|
|
|
|
*
|
|
|
|
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
|
|
|
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
|
|
|
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
|
|
|
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
|
|
|
|
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
|
|
|
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
|
|
|
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
|
|
|
|
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
|
|
|
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
|
|
|
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
|
|
|
* POSSIBILITY OF SUCH DAMAGE.
|
|
|
|
*/
|
|
|
|
|
|
|
|
#define REDISMODULE_EXPERIMENTAL_API
|
|
|
|
#include "redismodule.h"
|
2019-10-03 07:23:48 -04:00
|
|
|
#include <pthread.h>
|
2019-10-03 07:06:09 -04:00
|
|
|
|
|
|
|
/* Timer callback. */
|
|
|
|
void timerHandler(RedisModuleCtx *ctx, void *data) {
|
|
|
|
REDISMODULE_NOT_USED(ctx);
|
|
|
|
REDISMODULE_NOT_USED(data);
|
|
|
|
|
|
|
|
static int times = 0;
|
|
|
|
|
|
|
|
RedisModule_Replicate(ctx,"INCR","c","timer");
|
|
|
|
times++;
|
|
|
|
|
Remove read-only flag from non-keyspace cmds, different approach for EXEC to propagate MULTI (#8216)
In the distant history there was only the read flag for commands, and whatever
command that didn't have the read flag was a write one.
Then we added the write flag, but some portions of the code still used !read
Also some commands that don't work on the keyspace at all, still have the read
flag.
Changes in this commit:
1. remove the read-only flag from TIME, ECHO, ROLE and LASTSAVE
2. EXEC command used to decides if it should propagate a MULTI by looking at
the command flags (!read & !admin).
When i was about to change it to look at the write flag instead, i realized
that this would cause it not to propagate a MULTI for PUBLISH, EVAL, and
SCRIPT, all 3 are not marked as either a read command or a write one (as
they should), but all 3 are calling forceCommandPropagation.
So instead of introducing a new flag to denote a command that "writes" but
not into the keyspace, and still needs propagation, i decided to rely on
the forceCommandPropagation, and just fix the code to propagate MULTI when
needed rather than depending on the command flags at all.
The implication of my change then is that now it won't decide to propagate
MULTI when it sees one of these: SELECT, PING, INFO, COMMAND, TIME and
other commands which are neither read nor write.
3. Changing getNodeByQuery and clusterRedirectBlockedClientIfNeeded in
cluster.c to look at !write rather than read flag.
This should have no implications, since these code paths are only reachable
for commands which access keys, and these are always marked as either read
or write.
This commit improve MULTI propagation tests, for modules and a bunch of
other special cases, all of which used to pass already before that commit.
the only one that test change that uncovered a change of behavior is the
one that DELs a non-existing key, it used to propagate an empty
multi-exec block, and no longer does.
2020-12-22 05:03:49 -05:00
|
|
|
if (times < 3)
|
2019-10-03 07:06:09 -04:00
|
|
|
RedisModule_CreateTimer(ctx,100,timerHandler,NULL);
|
2019-10-03 07:23:48 -04:00
|
|
|
else
|
|
|
|
times = 0;
|
|
|
|
}
|
|
|
|
|
Remove read-only flag from non-keyspace cmds, different approach for EXEC to propagate MULTI (#8216)
In the distant history there was only the read flag for commands, and whatever
command that didn't have the read flag was a write one.
Then we added the write flag, but some portions of the code still used !read
Also some commands that don't work on the keyspace at all, still have the read
flag.
Changes in this commit:
1. remove the read-only flag from TIME, ECHO, ROLE and LASTSAVE
2. EXEC command used to decides if it should propagate a MULTI by looking at
the command flags (!read & !admin).
When i was about to change it to look at the write flag instead, i realized
that this would cause it not to propagate a MULTI for PUBLISH, EVAL, and
SCRIPT, all 3 are not marked as either a read command or a write one (as
they should), but all 3 are calling forceCommandPropagation.
So instead of introducing a new flag to denote a command that "writes" but
not into the keyspace, and still needs propagation, i decided to rely on
the forceCommandPropagation, and just fix the code to propagate MULTI when
needed rather than depending on the command flags at all.
The implication of my change then is that now it won't decide to propagate
MULTI when it sees one of these: SELECT, PING, INFO, COMMAND, TIME and
other commands which are neither read nor write.
3. Changing getNodeByQuery and clusterRedirectBlockedClientIfNeeded in
cluster.c to look at !write rather than read flag.
This should have no implications, since these code paths are only reachable
for commands which access keys, and these are always marked as either read
or write.
This commit improve MULTI propagation tests, for modules and a bunch of
other special cases, all of which used to pass already before that commit.
the only one that test change that uncovered a change of behavior is the
one that DELs a non-existing key, it used to propagate an empty
multi-exec block, and no longer does.
2020-12-22 05:03:49 -05:00
|
|
|
int propagateTestTimerCommand(RedisModuleCtx *ctx, RedisModuleString **argv, int argc)
|
|
|
|
{
|
|
|
|
REDISMODULE_NOT_USED(argv);
|
|
|
|
REDISMODULE_NOT_USED(argc);
|
|
|
|
|
|
|
|
RedisModuleTimerID timer_id =
|
|
|
|
RedisModule_CreateTimer(ctx,100,timerHandler,NULL);
|
|
|
|
REDISMODULE_NOT_USED(timer_id);
|
|
|
|
|
|
|
|
RedisModule_ReplyWithSimpleString(ctx,"OK");
|
|
|
|
return REDISMODULE_OK;
|
|
|
|
}
|
|
|
|
|
2021-03-10 11:02:17 -05:00
|
|
|
/* Timer callback. */
|
|
|
|
void timerNestedHandler(RedisModuleCtx *ctx, void *data) {
|
|
|
|
int repl = (long long)data;
|
|
|
|
|
|
|
|
/* The goal is the trigger a module command that calls RM_Replicate
|
|
|
|
* in order to test MULTI/EXEC structre */
|
|
|
|
RedisModule_Replicate(ctx,"INCRBY","cc","timer-nested-start","1");
|
2021-03-11 06:50:13 -05:00
|
|
|
RedisModuleCallReply *reply = RedisModule_Call(ctx,"propagate-test.nested", repl? "!" : "");
|
|
|
|
RedisModule_FreeCallReply(reply);
|
2021-03-10 11:02:17 -05:00
|
|
|
RedisModule_Replicate(ctx,"INCRBY","cc","timer-nested-end","1");
|
|
|
|
}
|
|
|
|
|
|
|
|
int propagateTestTimerNestedCommand(RedisModuleCtx *ctx, RedisModuleString **argv, int argc)
|
|
|
|
{
|
|
|
|
REDISMODULE_NOT_USED(argv);
|
|
|
|
REDISMODULE_NOT_USED(argc);
|
|
|
|
|
|
|
|
RedisModuleTimerID timer_id =
|
|
|
|
RedisModule_CreateTimer(ctx,100,timerNestedHandler,(void*)0);
|
|
|
|
REDISMODULE_NOT_USED(timer_id);
|
|
|
|
|
|
|
|
RedisModule_ReplyWithSimpleString(ctx,"OK");
|
|
|
|
return REDISMODULE_OK;
|
|
|
|
}
|
|
|
|
|
|
|
|
int propagateTestTimerNestedReplCommand(RedisModuleCtx *ctx, RedisModuleString **argv, int argc)
|
|
|
|
{
|
|
|
|
REDISMODULE_NOT_USED(argv);
|
|
|
|
REDISMODULE_NOT_USED(argc);
|
|
|
|
|
|
|
|
RedisModuleTimerID timer_id =
|
|
|
|
RedisModule_CreateTimer(ctx,100,timerNestedHandler,(void*)1);
|
|
|
|
REDISMODULE_NOT_USED(timer_id);
|
|
|
|
|
|
|
|
RedisModule_ReplyWithSimpleString(ctx,"OK");
|
|
|
|
return REDISMODULE_OK;
|
|
|
|
}
|
|
|
|
|
2019-10-03 07:23:48 -04:00
|
|
|
/* The thread entry point. */
|
|
|
|
void *threadMain(void *arg) {
|
|
|
|
REDISMODULE_NOT_USED(arg);
|
|
|
|
RedisModuleCtx *ctx = RedisModule_GetThreadSafeContext(NULL);
|
2019-10-03 12:44:47 -04:00
|
|
|
RedisModule_SelectDb(ctx,9); /* Tests ran in database number 9. */
|
Remove read-only flag from non-keyspace cmds, different approach for EXEC to propagate MULTI (#8216)
In the distant history there was only the read flag for commands, and whatever
command that didn't have the read flag was a write one.
Then we added the write flag, but some portions of the code still used !read
Also some commands that don't work on the keyspace at all, still have the read
flag.
Changes in this commit:
1. remove the read-only flag from TIME, ECHO, ROLE and LASTSAVE
2. EXEC command used to decides if it should propagate a MULTI by looking at
the command flags (!read & !admin).
When i was about to change it to look at the write flag instead, i realized
that this would cause it not to propagate a MULTI for PUBLISH, EVAL, and
SCRIPT, all 3 are not marked as either a read command or a write one (as
they should), but all 3 are calling forceCommandPropagation.
So instead of introducing a new flag to denote a command that "writes" but
not into the keyspace, and still needs propagation, i decided to rely on
the forceCommandPropagation, and just fix the code to propagate MULTI when
needed rather than depending on the command flags at all.
The implication of my change then is that now it won't decide to propagate
MULTI when it sees one of these: SELECT, PING, INFO, COMMAND, TIME and
other commands which are neither read nor write.
3. Changing getNodeByQuery and clusterRedirectBlockedClientIfNeeded in
cluster.c to look at !write rather than read flag.
This should have no implications, since these code paths are only reachable
for commands which access keys, and these are always marked as either read
or write.
This commit improve MULTI propagation tests, for modules and a bunch of
other special cases, all of which used to pass already before that commit.
the only one that test change that uncovered a change of behavior is the
one that DELs a non-existing key, it used to propagate an empty
multi-exec block, and no longer does.
2020-12-22 05:03:49 -05:00
|
|
|
for (int i = 0; i < 3; i++) {
|
2019-10-03 07:23:48 -04:00
|
|
|
RedisModule_ThreadSafeContextLock(ctx);
|
2020-03-31 06:04:06 -04:00
|
|
|
RedisModule_Replicate(ctx,"INCR","c","a-from-thread");
|
|
|
|
RedisModule_Replicate(ctx,"INCR","c","b-from-thread");
|
2019-10-03 07:23:48 -04:00
|
|
|
RedisModule_ThreadSafeContextUnlock(ctx);
|
|
|
|
}
|
|
|
|
RedisModule_FreeThreadSafeContext(ctx);
|
|
|
|
return NULL;
|
2019-10-03 07:06:09 -04:00
|
|
|
}
|
|
|
|
|
Remove read-only flag from non-keyspace cmds, different approach for EXEC to propagate MULTI (#8216)
In the distant history there was only the read flag for commands, and whatever
command that didn't have the read flag was a write one.
Then we added the write flag, but some portions of the code still used !read
Also some commands that don't work on the keyspace at all, still have the read
flag.
Changes in this commit:
1. remove the read-only flag from TIME, ECHO, ROLE and LASTSAVE
2. EXEC command used to decides if it should propagate a MULTI by looking at
the command flags (!read & !admin).
When i was about to change it to look at the write flag instead, i realized
that this would cause it not to propagate a MULTI for PUBLISH, EVAL, and
SCRIPT, all 3 are not marked as either a read command or a write one (as
they should), but all 3 are calling forceCommandPropagation.
So instead of introducing a new flag to denote a command that "writes" but
not into the keyspace, and still needs propagation, i decided to rely on
the forceCommandPropagation, and just fix the code to propagate MULTI when
needed rather than depending on the command flags at all.
The implication of my change then is that now it won't decide to propagate
MULTI when it sees one of these: SELECT, PING, INFO, COMMAND, TIME and
other commands which are neither read nor write.
3. Changing getNodeByQuery and clusterRedirectBlockedClientIfNeeded in
cluster.c to look at !write rather than read flag.
This should have no implications, since these code paths are only reachable
for commands which access keys, and these are always marked as either read
or write.
This commit improve MULTI propagation tests, for modules and a bunch of
other special cases, all of which used to pass already before that commit.
the only one that test change that uncovered a change of behavior is the
one that DELs a non-existing key, it used to propagate an empty
multi-exec block, and no longer does.
2020-12-22 05:03:49 -05:00
|
|
|
int propagateTestThreadCommand(RedisModuleCtx *ctx, RedisModuleString **argv, int argc)
|
2019-10-03 07:06:09 -04:00
|
|
|
{
|
|
|
|
REDISMODULE_NOT_USED(argv);
|
|
|
|
REDISMODULE_NOT_USED(argc);
|
|
|
|
|
2019-10-03 07:23:48 -04:00
|
|
|
pthread_t tid;
|
|
|
|
if (pthread_create(&tid,NULL,threadMain,NULL) != 0)
|
|
|
|
return RedisModule_ReplyWithError(ctx,"-ERR Can't start thread");
|
2019-10-03 07:06:09 -04:00
|
|
|
REDISMODULE_NOT_USED(tid);
|
|
|
|
|
|
|
|
RedisModule_ReplyWithSimpleString(ctx,"OK");
|
|
|
|
return REDISMODULE_OK;
|
|
|
|
}
|
|
|
|
|
Remove read-only flag from non-keyspace cmds, different approach for EXEC to propagate MULTI (#8216)
In the distant history there was only the read flag for commands, and whatever
command that didn't have the read flag was a write one.
Then we added the write flag, but some portions of the code still used !read
Also some commands that don't work on the keyspace at all, still have the read
flag.
Changes in this commit:
1. remove the read-only flag from TIME, ECHO, ROLE and LASTSAVE
2. EXEC command used to decides if it should propagate a MULTI by looking at
the command flags (!read & !admin).
When i was about to change it to look at the write flag instead, i realized
that this would cause it not to propagate a MULTI for PUBLISH, EVAL, and
SCRIPT, all 3 are not marked as either a read command or a write one (as
they should), but all 3 are calling forceCommandPropagation.
So instead of introducing a new flag to denote a command that "writes" but
not into the keyspace, and still needs propagation, i decided to rely on
the forceCommandPropagation, and just fix the code to propagate MULTI when
needed rather than depending on the command flags at all.
The implication of my change then is that now it won't decide to propagate
MULTI when it sees one of these: SELECT, PING, INFO, COMMAND, TIME and
other commands which are neither read nor write.
3. Changing getNodeByQuery and clusterRedirectBlockedClientIfNeeded in
cluster.c to look at !write rather than read flag.
This should have no implications, since these code paths are only reachable
for commands which access keys, and these are always marked as either read
or write.
This commit improve MULTI propagation tests, for modules and a bunch of
other special cases, all of which used to pass already before that commit.
the only one that test change that uncovered a change of behavior is the
one that DELs a non-existing key, it used to propagate an empty
multi-exec block, and no longer does.
2020-12-22 05:03:49 -05:00
|
|
|
int propagateTestSimpleCommand(RedisModuleCtx *ctx, RedisModuleString **argv, int argc)
|
2020-03-31 05:00:45 -04:00
|
|
|
{
|
|
|
|
REDISMODULE_NOT_USED(argv);
|
|
|
|
REDISMODULE_NOT_USED(argc);
|
|
|
|
|
2020-03-31 06:04:06 -04:00
|
|
|
/* Replicate two commands to test MULTI/EXEC wrapping. */
|
|
|
|
RedisModule_Replicate(ctx,"INCR","c","counter-1");
|
|
|
|
RedisModule_Replicate(ctx,"INCR","c","counter-2");
|
|
|
|
RedisModule_ReplyWithSimpleString(ctx,"OK");
|
|
|
|
return REDISMODULE_OK;
|
|
|
|
}
|
|
|
|
|
Remove read-only flag from non-keyspace cmds, different approach for EXEC to propagate MULTI (#8216)
In the distant history there was only the read flag for commands, and whatever
command that didn't have the read flag was a write one.
Then we added the write flag, but some portions of the code still used !read
Also some commands that don't work on the keyspace at all, still have the read
flag.
Changes in this commit:
1. remove the read-only flag from TIME, ECHO, ROLE and LASTSAVE
2. EXEC command used to decides if it should propagate a MULTI by looking at
the command flags (!read & !admin).
When i was about to change it to look at the write flag instead, i realized
that this would cause it not to propagate a MULTI for PUBLISH, EVAL, and
SCRIPT, all 3 are not marked as either a read command or a write one (as
they should), but all 3 are calling forceCommandPropagation.
So instead of introducing a new flag to denote a command that "writes" but
not into the keyspace, and still needs propagation, i decided to rely on
the forceCommandPropagation, and just fix the code to propagate MULTI when
needed rather than depending on the command flags at all.
The implication of my change then is that now it won't decide to propagate
MULTI when it sees one of these: SELECT, PING, INFO, COMMAND, TIME and
other commands which are neither read nor write.
3. Changing getNodeByQuery and clusterRedirectBlockedClientIfNeeded in
cluster.c to look at !write rather than read flag.
This should have no implications, since these code paths are only reachable
for commands which access keys, and these are always marked as either read
or write.
This commit improve MULTI propagation tests, for modules and a bunch of
other special cases, all of which used to pass already before that commit.
the only one that test change that uncovered a change of behavior is the
one that DELs a non-existing key, it used to propagate an empty
multi-exec block, and no longer does.
2020-12-22 05:03:49 -05:00
|
|
|
int propagateTestMixedCommand(RedisModuleCtx *ctx, RedisModuleString **argv, int argc)
|
2020-03-31 06:04:06 -04:00
|
|
|
{
|
|
|
|
REDISMODULE_NOT_USED(argv);
|
|
|
|
REDISMODULE_NOT_USED(argc);
|
|
|
|
RedisModuleCallReply *reply;
|
|
|
|
|
|
|
|
/* This test mixes multiple propagation systems. */
|
|
|
|
reply = RedisModule_Call(ctx, "INCR", "c!", "using-call");
|
|
|
|
RedisModule_FreeCallReply(reply);
|
|
|
|
|
|
|
|
RedisModule_Replicate(ctx,"INCR","c","counter-1");
|
|
|
|
RedisModule_Replicate(ctx,"INCR","c","counter-2");
|
|
|
|
|
|
|
|
reply = RedisModule_Call(ctx, "INCR", "c!", "after-call");
|
|
|
|
RedisModule_FreeCallReply(reply);
|
|
|
|
|
2020-03-31 05:00:45 -04:00
|
|
|
RedisModule_ReplyWithSimpleString(ctx,"OK");
|
|
|
|
return REDISMODULE_OK;
|
|
|
|
}
|
|
|
|
|
2021-03-10 11:02:17 -05:00
|
|
|
int propagateTestNestedCommand(RedisModuleCtx *ctx, RedisModuleString **argv, int argc)
|
|
|
|
{
|
|
|
|
REDISMODULE_NOT_USED(argv);
|
|
|
|
REDISMODULE_NOT_USED(argc);
|
|
|
|
RedisModuleCallReply *reply;
|
|
|
|
|
|
|
|
/* This test mixes multiple propagation systems. */
|
|
|
|
reply = RedisModule_Call(ctx, "INCR", "c!", "using-call");
|
|
|
|
RedisModule_FreeCallReply(reply);
|
|
|
|
|
2021-03-11 06:50:13 -05:00
|
|
|
reply = RedisModule_Call(ctx,"propagate-test.simple", "!");
|
|
|
|
RedisModule_FreeCallReply(reply);
|
2021-03-10 11:02:17 -05:00
|
|
|
|
|
|
|
RedisModule_Replicate(ctx,"INCR","c","counter-3");
|
|
|
|
RedisModule_Replicate(ctx,"INCR","c","counter-4");
|
|
|
|
|
|
|
|
reply = RedisModule_Call(ctx, "INCR", "c!", "after-call");
|
|
|
|
RedisModule_FreeCallReply(reply);
|
|
|
|
|
|
|
|
RedisModule_ReplyWithSimpleString(ctx,"OK");
|
|
|
|
return REDISMODULE_OK;
|
|
|
|
}
|
|
|
|
|
2019-10-03 07:06:09 -04:00
|
|
|
int RedisModule_OnLoad(RedisModuleCtx *ctx, RedisModuleString **argv, int argc) {
|
|
|
|
REDISMODULE_NOT_USED(argv);
|
|
|
|
REDISMODULE_NOT_USED(argc);
|
|
|
|
|
|
|
|
if (RedisModule_Init(ctx,"propagate-test",1,REDISMODULE_APIVER_1)
|
|
|
|
== REDISMODULE_ERR) return REDISMODULE_ERR;
|
|
|
|
|
Remove read-only flag from non-keyspace cmds, different approach for EXEC to propagate MULTI (#8216)
In the distant history there was only the read flag for commands, and whatever
command that didn't have the read flag was a write one.
Then we added the write flag, but some portions of the code still used !read
Also some commands that don't work on the keyspace at all, still have the read
flag.
Changes in this commit:
1. remove the read-only flag from TIME, ECHO, ROLE and LASTSAVE
2. EXEC command used to decides if it should propagate a MULTI by looking at
the command flags (!read & !admin).
When i was about to change it to look at the write flag instead, i realized
that this would cause it not to propagate a MULTI for PUBLISH, EVAL, and
SCRIPT, all 3 are not marked as either a read command or a write one (as
they should), but all 3 are calling forceCommandPropagation.
So instead of introducing a new flag to denote a command that "writes" but
not into the keyspace, and still needs propagation, i decided to rely on
the forceCommandPropagation, and just fix the code to propagate MULTI when
needed rather than depending on the command flags at all.
The implication of my change then is that now it won't decide to propagate
MULTI when it sees one of these: SELECT, PING, INFO, COMMAND, TIME and
other commands which are neither read nor write.
3. Changing getNodeByQuery and clusterRedirectBlockedClientIfNeeded in
cluster.c to look at !write rather than read flag.
This should have no implications, since these code paths are only reachable
for commands which access keys, and these are always marked as either read
or write.
This commit improve MULTI propagation tests, for modules and a bunch of
other special cases, all of which used to pass already before that commit.
the only one that test change that uncovered a change of behavior is the
one that DELs a non-existing key, it used to propagate an empty
multi-exec block, and no longer does.
2020-12-22 05:03:49 -05:00
|
|
|
if (RedisModule_CreateCommand(ctx,"propagate-test.timer",
|
|
|
|
propagateTestTimerCommand,
|
|
|
|
"",1,1,1) == REDISMODULE_ERR)
|
|
|
|
return REDISMODULE_ERR;
|
|
|
|
|
2021-03-10 11:02:17 -05:00
|
|
|
if (RedisModule_CreateCommand(ctx,"propagate-test.timer-nested",
|
|
|
|
propagateTestTimerNestedCommand,
|
|
|
|
"",1,1,1) == REDISMODULE_ERR)
|
|
|
|
return REDISMODULE_ERR;
|
|
|
|
|
|
|
|
if (RedisModule_CreateCommand(ctx,"propagate-test.timer-nested-repl",
|
|
|
|
propagateTestTimerNestedReplCommand,
|
|
|
|
"",1,1,1) == REDISMODULE_ERR)
|
|
|
|
return REDISMODULE_ERR;
|
|
|
|
|
Remove read-only flag from non-keyspace cmds, different approach for EXEC to propagate MULTI (#8216)
In the distant history there was only the read flag for commands, and whatever
command that didn't have the read flag was a write one.
Then we added the write flag, but some portions of the code still used !read
Also some commands that don't work on the keyspace at all, still have the read
flag.
Changes in this commit:
1. remove the read-only flag from TIME, ECHO, ROLE and LASTSAVE
2. EXEC command used to decides if it should propagate a MULTI by looking at
the command flags (!read & !admin).
When i was about to change it to look at the write flag instead, i realized
that this would cause it not to propagate a MULTI for PUBLISH, EVAL, and
SCRIPT, all 3 are not marked as either a read command or a write one (as
they should), but all 3 are calling forceCommandPropagation.
So instead of introducing a new flag to denote a command that "writes" but
not into the keyspace, and still needs propagation, i decided to rely on
the forceCommandPropagation, and just fix the code to propagate MULTI when
needed rather than depending on the command flags at all.
The implication of my change then is that now it won't decide to propagate
MULTI when it sees one of these: SELECT, PING, INFO, COMMAND, TIME and
other commands which are neither read nor write.
3. Changing getNodeByQuery and clusterRedirectBlockedClientIfNeeded in
cluster.c to look at !write rather than read flag.
This should have no implications, since these code paths are only reachable
for commands which access keys, and these are always marked as either read
or write.
This commit improve MULTI propagation tests, for modules and a bunch of
other special cases, all of which used to pass already before that commit.
the only one that test change that uncovered a change of behavior is the
one that DELs a non-existing key, it used to propagate an empty
multi-exec block, and no longer does.
2020-12-22 05:03:49 -05:00
|
|
|
if (RedisModule_CreateCommand(ctx,"propagate-test.thread",
|
|
|
|
propagateTestThreadCommand,
|
2019-10-03 07:06:09 -04:00
|
|
|
"",1,1,1) == REDISMODULE_ERR)
|
|
|
|
return REDISMODULE_ERR;
|
2020-03-31 05:00:45 -04:00
|
|
|
|
Remove read-only flag from non-keyspace cmds, different approach for EXEC to propagate MULTI (#8216)
In the distant history there was only the read flag for commands, and whatever
command that didn't have the read flag was a write one.
Then we added the write flag, but some portions of the code still used !read
Also some commands that don't work on the keyspace at all, still have the read
flag.
Changes in this commit:
1. remove the read-only flag from TIME, ECHO, ROLE and LASTSAVE
2. EXEC command used to decides if it should propagate a MULTI by looking at
the command flags (!read & !admin).
When i was about to change it to look at the write flag instead, i realized
that this would cause it not to propagate a MULTI for PUBLISH, EVAL, and
SCRIPT, all 3 are not marked as either a read command or a write one (as
they should), but all 3 are calling forceCommandPropagation.
So instead of introducing a new flag to denote a command that "writes" but
not into the keyspace, and still needs propagation, i decided to rely on
the forceCommandPropagation, and just fix the code to propagate MULTI when
needed rather than depending on the command flags at all.
The implication of my change then is that now it won't decide to propagate
MULTI when it sees one of these: SELECT, PING, INFO, COMMAND, TIME and
other commands which are neither read nor write.
3. Changing getNodeByQuery and clusterRedirectBlockedClientIfNeeded in
cluster.c to look at !write rather than read flag.
This should have no implications, since these code paths are only reachable
for commands which access keys, and these are always marked as either read
or write.
This commit improve MULTI propagation tests, for modules and a bunch of
other special cases, all of which used to pass already before that commit.
the only one that test change that uncovered a change of behavior is the
one that DELs a non-existing key, it used to propagate an empty
multi-exec block, and no longer does.
2020-12-22 05:03:49 -05:00
|
|
|
if (RedisModule_CreateCommand(ctx,"propagate-test.simple",
|
|
|
|
propagateTestSimpleCommand,
|
2020-03-31 05:00:45 -04:00
|
|
|
"",1,1,1) == REDISMODULE_ERR)
|
|
|
|
return REDISMODULE_ERR;
|
|
|
|
|
Remove read-only flag from non-keyspace cmds, different approach for EXEC to propagate MULTI (#8216)
In the distant history there was only the read flag for commands, and whatever
command that didn't have the read flag was a write one.
Then we added the write flag, but some portions of the code still used !read
Also some commands that don't work on the keyspace at all, still have the read
flag.
Changes in this commit:
1. remove the read-only flag from TIME, ECHO, ROLE and LASTSAVE
2. EXEC command used to decides if it should propagate a MULTI by looking at
the command flags (!read & !admin).
When i was about to change it to look at the write flag instead, i realized
that this would cause it not to propagate a MULTI for PUBLISH, EVAL, and
SCRIPT, all 3 are not marked as either a read command or a write one (as
they should), but all 3 are calling forceCommandPropagation.
So instead of introducing a new flag to denote a command that "writes" but
not into the keyspace, and still needs propagation, i decided to rely on
the forceCommandPropagation, and just fix the code to propagate MULTI when
needed rather than depending on the command flags at all.
The implication of my change then is that now it won't decide to propagate
MULTI when it sees one of these: SELECT, PING, INFO, COMMAND, TIME and
other commands which are neither read nor write.
3. Changing getNodeByQuery and clusterRedirectBlockedClientIfNeeded in
cluster.c to look at !write rather than read flag.
This should have no implications, since these code paths are only reachable
for commands which access keys, and these are always marked as either read
or write.
This commit improve MULTI propagation tests, for modules and a bunch of
other special cases, all of which used to pass already before that commit.
the only one that test change that uncovered a change of behavior is the
one that DELs a non-existing key, it used to propagate an empty
multi-exec block, and no longer does.
2020-12-22 05:03:49 -05:00
|
|
|
if (RedisModule_CreateCommand(ctx,"propagate-test.mixed",
|
|
|
|
propagateTestMixedCommand,
|
2020-03-31 06:04:06 -04:00
|
|
|
"",1,1,1) == REDISMODULE_ERR)
|
|
|
|
return REDISMODULE_ERR;
|
|
|
|
|
2021-03-10 11:02:17 -05:00
|
|
|
if (RedisModule_CreateCommand(ctx,"propagate-test.nested",
|
|
|
|
propagateTestNestedCommand,
|
|
|
|
"",1,1,1) == REDISMODULE_ERR)
|
|
|
|
return REDISMODULE_ERR;
|
|
|
|
|
2019-10-03 07:06:09 -04:00
|
|
|
return REDISMODULE_OK;
|
|
|
|
}
|