Unverified Commit b08fd9f9 authored by YaacovHazan's avatar YaacovHazan Committed by GitHub
Browse files

Merge unstable into 8.0 (#13622)

parents 30eb6c32 dd20aa51
......@@ -747,7 +747,7 @@ GetFieldRes hashTypeGetValue(redisDb *db, robj *o, sds field, unsigned char **vs
}
if ((server.loading) ||
(server.lazy_expire_disabled) ||
(server.allow_access_expired) ||
(hfeFlags & HFE_LAZY_AVOID_FIELD_DEL) ||
(isPausedActionsWithUpdate(PAUSE_ACTION_EXPIRE)))
return GETF_EXPIRED;
......@@ -1929,7 +1929,7 @@ static int hashTypeExpireIfNeeded(redisDb *db, robj *o) {
/* Follow expireIfNeeded() conditions of when not lazy-expire */
if ( (server.loading) ||
(server.lazy_expire_disabled) ||
(server.allow_access_expired) ||
(server.masterhost) || /* master-client or user-client, don't delete */
(isPausedActionsWithUpdate(PAUSE_ACTION_EXPIRE)))
return 0;
......
......@@ -56,8 +56,11 @@
/* Glob-style pattern matching. */
static int stringmatchlen_impl(const char *pattern, int patternLen,
const char *string, int stringLen, int nocase, int *skipLongerMatches)
const char *string, int stringLen, int nocase, int *skipLongerMatches, int nesting)
{
/* Protection against abusive patterns. */
if (nesting > 1000) return 0;
while(patternLen && stringLen) {
switch(pattern[0]) {
case '*':
......@@ -69,7 +72,7 @@ static int stringmatchlen_impl(const char *pattern, int patternLen,
return 1; /* match */
while(stringLen) {
if (stringmatchlen_impl(pattern+1, patternLen-1,
string, stringLen, nocase, skipLongerMatches))
string, stringLen, nocase, skipLongerMatches, nesting+1))
return 1; /* match */
if (*skipLongerMatches)
return 0; /* no match */
......@@ -191,7 +194,7 @@ static int stringmatchlen_impl(const char *pattern, int patternLen,
int stringmatchlen(const char *pattern, int patternLen,
const char *string, int stringLen, int nocase) {
int skipLongerMatches = 0;
return stringmatchlen_impl(pattern,patternLen,string,stringLen,nocase,&skipLongerMatches);
return stringmatchlen_impl(pattern,patternLen,string,stringLen,nocase,&skipLongerMatches,0);
}
int stringmatch(const char *pattern, const char *string, int nocase) {
......
......@@ -6,6 +6,9 @@ if {$::singledb} {
set ::dbnum 9
}
file delete ./.rediscli_history_test
set ::env(REDISCLI_HISTFILE) ".rediscli_history_test"
start_server {tags {"cli"}} {
proc open_cli {{opts ""} {infile ""}} {
if { $opts == "" } {
......@@ -68,10 +71,8 @@ start_server {tags {"cli"}} {
set _ [format_output [read_cli $fd]]
}
file delete ./.rediscli_history_test
proc test_interactive_cli_with_prompt {name code} {
set ::env(FAKETTY_WITH_PROMPT) 1
set ::env(REDISCLI_HISTFILE) ".rediscli_history_test"
test_interactive_cli $name $code
unset ::env(FAKETTY_WITH_PROMPT)
}
......@@ -839,3 +840,4 @@ start_server {tags {"cli external:skip"}} {
}
}
file delete ./.rediscli_history_test
......@@ -241,6 +241,11 @@ proc tags_acceptable {tags err_return} {
return 0
}
if { [lsearch $tags "experimental"] >=0 && [lsearch $::allowtags "experimental"] == -1 } {
set err "experimental test not allowed"
return 0
}
return 1
}
......
......@@ -506,7 +506,7 @@ proc the_end {} {
}
}
# The client is not even driven (the test server is instead) as we just need
# The client is not event driven (the test server is instead) as we just need
# to read the command, execute, reply... all this in a loop.
proc test_client_main server_port {
set ::test_server_fd [socket localhost $server_port]
......
......@@ -107,3 +107,76 @@ test "DELSLOTSRANGE command with several boundary conditions test suite" {
assert_match "*9829 11000*12001 12100*12201 13104*" [$master4 CLUSTER SLOTS]
}
} cluster_allocate_with_continuous_slots_local
start_cluster 2 0 {tags {external:skip cluster experimental}} {
set master1 [srv 0 "client"]
set master2 [srv -1 "client"]
test "SFLUSH - Errors and output validation" {
assert_match "* 0-8191*" [$master1 CLUSTER NODES]
assert_match "* 8192-16383*" [$master2 CLUSTER NODES]
assert_match "*0 8191*" [$master1 CLUSTER SLOTS]
assert_match "*8192 16383*" [$master2 CLUSTER SLOTS]
# make master1 non-continuous slots
$master1 cluster DELSLOTSRANGE 1000 2000
# Test SFLUSH errors validation
assert_error {ERR wrong number of arguments*} {$master1 SFLUSH 4}
assert_error {ERR wrong number of arguments*} {$master1 SFLUSH 4 SYNC}
assert_error {ERR Invalid or out of range slot} {$master1 SFLUSH x 4}
assert_error {ERR Invalid or out of range slot} {$master1 SFLUSH 0 12x}
assert_error {ERR Slot 3 specified multiple times} {$master1 SFLUSH 2 4 3 5}
assert_error {ERR start slot number 8 is greater than*} {$master1 SFLUSH 8 4}
assert_error {ERR wrong number of arguments*} {$master1 SFLUSH 4 8 10}
assert_error {ERR wrong number of arguments*} {$master1 SFLUSH 0 999 2001 8191 ASYNCX}
# Test SFLUSH output validation
assert_match "" [$master1 SFLUSH 2 4]
assert_match "" [$master1 SFLUSH 0 4]
assert_match "" [$master2 SFLUSH 0 4]
assert_match "" [$master1 SFLUSH 1 8191]
assert_match "" [$master1 SFLUSH 0 8190]
assert_match "" [$master1 SFLUSH 0 998 2001 8191]
assert_match "" [$master1 SFLUSH 1 999 2001 8191]
assert_match "" [$master1 SFLUSH 0 999 2001 8190]
assert_match "" [$master1 SFLUSH 0 999 2002 8191]
assert_match "{0 999} {2001 8191}" [$master1 SFLUSH 0 999 2001 8191]
assert_match "{0 999} {2001 8191}" [$master1 SFLUSH 0 8191]
assert_match "{0 999} {2001 8191}" [$master1 SFLUSH 0 4000 4001 8191]
assert_match "" [$master2 SFLUSH 8193 16383]
assert_match "" [$master2 SFLUSH 8192 16382]
assert_match "{8192 16383}" [$master2 SFLUSH 8192 16383]
assert_match "{8192 16383}" [$master2 SFLUSH 8192 16383 SYNC]
assert_match "{8192 16383}" [$master2 SFLUSH 8192 16383 ASYNC]
assert_match "{8192 16383}" [$master2 SFLUSH 8192 9000 9001 16383]
assert_match "{8192 16383}" [$master2 SFLUSH 8192 9000 9001 16383 SYNC]
assert_match "{8192 16383}" [$master2 SFLUSH 8192 9000 9001 16383 ASYNC]
# restore master1 continuous slots
$master1 cluster ADDSLOTSRANGE 1000 2000
}
test "SFLUSH - Deletes the keys with argument <NONE>/SYNC/ASYNC" {
foreach op {"" "SYNC" "ASYNC"} {
for {set i 0} {$i < 100} {incr i} {
catch {$master1 SET key$i val$i}
catch {$master2 SET key$i val$i}
}
assert {[$master1 DBSIZE] > 0}
assert {[$master2 DBSIZE] > 0}
if {$op eq ""} {
assert_match "{0 8191}" [ $master1 SFLUSH 0 8191]
} else {
assert_match "{0 8191}" [ $master1 SFLUSH 0 8191 $op]
}
assert {[$master1 DBSIZE] == 0}
assert {[$master2 DBSIZE] > 0}
assert_match "{8192 16383}" [ $master2 SFLUSH 8192 16383]
assert {[$master2 DBSIZE] == 0}
}
}
}
......@@ -509,6 +509,12 @@ foreach {type large} [array get largevalue] {
r KEYS "a*a*a*a*a*a*a*a*a*a*a*a*a*a*a*a*a*a*a*a*b"
} {}
test {Regression for pattern matching very long nested loops} {
r flushdb
r SET [string repeat "a" 50000] 1
r KEYS [string repeat "*?" 50000]
} {}
test {Coverage: basic SWAPDB test and unhappy path} {
r flushall
r select 0
......
......@@ -691,6 +691,12 @@ start_server {tags {"scripting"}} {
set e
} {ERR *Attempt to modify a readonly table*}
test {lua bit.tohex bug} {
set res [run_script {return bit.tohex(65535, -2147483648)} 0]
r ping
set res
} {0000FFFF}
test {Test an example script DECR_IF_GT} {
set decr_if_gt {
local current
......
......@@ -73,7 +73,7 @@ start_server {
set result [create_random_dataset 16 lpush]
test "SORT GET #" {
assert_equal [lsort -integer $result] [r sort tosort GET #]
} {} {cluster:skip}
}
foreach command {SORT SORT_RO} {
test "$command GET <const>" {
......@@ -393,6 +393,11 @@ start_cluster 1 0 {tags {"external:skip cluster sort"}} {
r sort "{a}mylist" by "{a}by*" get "{a}get*"
} {30 200 100}
test "sort get # in cluster mode" {
assert_equal [r sort "{a}mylist" by "{a}by*" get # ] {3 1 2}
r sort "{a}mylist" by "{a}by*" get "{a}get*" get #
} {30 3 200 1 100 2}
test "sort_ro by in cluster mode" {
catch {r sort_ro "{a}mylist" by by*} e
assert_match {ERR BY option of SORT denied in Cluster mode when *} $e
......@@ -404,4 +409,9 @@ start_cluster 1 0 {tags {"external:skip cluster sort"}} {
assert_match {ERR GET option of SORT denied in Cluster mode when *} $e
r sort_ro "{a}mylist" by "{a}by*" get "{a}get*"
} {30 200 100}
test "sort_ro get # in cluster mode" {
assert_equal [r sort_ro "{a}mylist" by "{a}by*" get # ] {3 1 2}
r sort_ro "{a}mylist" by "{a}by*" get "{a}get*" get #
} {30 3 200 1 100 2}
}
......@@ -1454,6 +1454,8 @@ start_server {
assert_equal [dict get $group entries-read] 3
assert_equal [dict get $group lag] 0
wait_for_ofs_sync $master $replica
set reply [$replica XINFO STREAM mystream FULL]
set group [lindex [dict get $reply groups] 0]
assert_equal [dict get $group entries-read] 3
......
......@@ -517,6 +517,11 @@ class Subcommand(Command):
def create_command(name, desc):
flags = desc.get("command_flags")
if flags and "EXPERIMENTAL" in flags:
print("Command %s is experimental, skipping..." % name)
return
if desc.get("container"):
cmd = Subcommand(name.upper(), desc)
subcommands.setdefault(desc["container"].upper(), {})[name] = cmd
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment