redict/tests/unit/aofrw.tcl

225 lines
7.6 KiB
Tcl
Raw Normal View History

Improve test suite to handle external servers better. (#9033) This commit revives the improves the ability to run the test suite against external servers, instead of launching and managing `redis-server` processes as part of the test fixture. This capability existed in the past, using the `--host` and `--port` options. However, it was quite limited and mostly useful when running a specific tests. Attempting to run larger chunks of the test suite experienced many issues: * Many tests depend on being able to start and control `redis-server` themselves, and there's no clear distinction between external server compatible and other tests. * Cluster mode is not supported (resulting with `CROSSSLOT` errors). This PR cleans up many things and makes it possible to run the entire test suite against an external server. It also provides more fine grained controls to handle cases where the external server supports a subset of the Redis commands, limited number of databases, cluster mode, etc. The tests directory now contains a `README.md` file that describes how this works. This commit also includes additional cleanups and fixes: * Tests can now be tagged. * Tag-based selection is now unified across `start_server`, `tags` and `test`. * More information is provided about skipped or ignored tests. * Repeated patterns in tests have been extracted to common procedures, both at a global level and on a per-test file basis. * Cleaned up some cases where test setup was based on a previous test executing (a major anti-pattern that repeats itself in many places). * Cleaned up some cases where test teardown was not part of a test (in the future we should have dedicated teardown code that executes even when tests fail). * Fixed some tests that were flaky running on external servers.
2021-06-09 08:13:24 -04:00
start_server {tags {"aofrw external:skip"}} {
2014-07-10 05:24:59 -04:00
# Enable the AOF
r config set appendonly yes
r config set auto-aof-rewrite-percentage 0 ; # Disable auto-rewrite.
waitForBgrewriteaof r
foreach rdbpre {yes no} {
r config set aof-use-rdb-preamble $rdbpre
test "AOF rewrite during write load: RDB preamble=$rdbpre" {
# Start a write load for 10 seconds
set master [srv 0 client]
set master_host [srv 0 host]
set master_port [srv 0 port]
set load_handle0 [start_write_load $master_host $master_port 10]
set load_handle1 [start_write_load $master_host $master_port 10]
set load_handle2 [start_write_load $master_host $master_port 10]
set load_handle3 [start_write_load $master_host $master_port 10]
set load_handle4 [start_write_load $master_host $master_port 10]
2014-07-10 05:24:59 -04:00
# Make sure the instance is really receiving data
wait_for_condition 50 100 {
[r dbsize] > 0
} else {
fail "No write load detected."
}
2014-07-10 05:24:59 -04:00
# After 3 seconds, start a rewrite, while the write load is still
# active.
after 3000
r bgrewriteaof
waitForBgrewriteaof r
2014-07-10 05:24:59 -04:00
# Let it run a bit more so that we'll append some data to the new
# AOF.
after 1000
2014-07-10 05:24:59 -04:00
# Stop the processes generating the load if they are still active
stop_write_load $load_handle0
stop_write_load $load_handle1
stop_write_load $load_handle2
stop_write_load $load_handle3
stop_write_load $load_handle4
2014-07-10 05:24:59 -04:00
# Make sure no more commands processed, before taking debug digest
wait_load_handlers_disconnected
# Get the data set digest
set d1 [debug_digest]
2014-07-10 05:24:59 -04:00
# Load the AOF
r debug loadaof
set d2 [debug_digest]
2014-07-10 05:24:59 -04:00
# Make sure they are the same
assert {$d1 eq $d2}
}
2014-07-10 05:24:59 -04:00
}
}
Improve test suite to handle external servers better. (#9033) This commit revives the improves the ability to run the test suite against external servers, instead of launching and managing `redis-server` processes as part of the test fixture. This capability existed in the past, using the `--host` and `--port` options. However, it was quite limited and mostly useful when running a specific tests. Attempting to run larger chunks of the test suite experienced many issues: * Many tests depend on being able to start and control `redis-server` themselves, and there's no clear distinction between external server compatible and other tests. * Cluster mode is not supported (resulting with `CROSSSLOT` errors). This PR cleans up many things and makes it possible to run the entire test suite against an external server. It also provides more fine grained controls to handle cases where the external server supports a subset of the Redis commands, limited number of databases, cluster mode, etc. The tests directory now contains a `README.md` file that describes how this works. This commit also includes additional cleanups and fixes: * Tests can now be tagged. * Tag-based selection is now unified across `start_server`, `tags` and `test`. * More information is provided about skipped or ignored tests. * Repeated patterns in tests have been extracted to common procedures, both at a global level and on a per-test file basis. * Cleaned up some cases where test setup was based on a previous test executing (a major anti-pattern that repeats itself in many places). * Cleaned up some cases where test teardown was not part of a test (in the future we should have dedicated teardown code that executes even when tests fail). * Fixed some tests that were flaky running on external servers.
2021-06-09 08:13:24 -04:00
start_server {tags {"aofrw external:skip"} overrides {aof-use-rdb-preamble no}} {
test {Turning off AOF kills the background writing child if any} {
r config set appendonly yes
waitForBgrewriteaof r
# start a slow AOFRW
r set k v
r config set rdb-key-save-delay 10000000
r bgrewriteaof
# disable AOF and wait for the child to be killed
r config set appendonly no
wait_for_condition 50 100 {
[string match {*Killing*AOF*child*} [exec tail -5 < [srv 0 stdout]]]
} else {
fail "Can't find 'Killing AOF child' into recent logs"
}
r config set rdb-key-save-delay 0
}
2011-12-12 09:34:00 -05:00
foreach d {string int} {
foreach e {quicklist} {
2011-12-12 09:34:00 -05:00
test "AOF rewrite of list with $e encoding, $d data" {
r flushall
set len 1000
2011-12-12 09:34:00 -05:00
for {set j 0} {$j < $len} {incr j} {
if {$d eq {string}} {
set data [randstring 0 16 alpha]
} else {
set data [randomInt 4000000000]
}
r lpush key $data
}
assert_equal [r object encoding key] $e
set d1 [debug_digest]
2011-12-12 09:34:00 -05:00
r bgrewriteaof
waitForBgrewriteaof r
r debug loadaof
set d2 [debug_digest]
2011-12-12 09:34:00 -05:00
if {$d1 ne $d2} {
error "assertion:$d1 is not equal to $d2"
}
}
}
}
foreach d {string int} {
foreach e {intset hashtable} {
test "AOF rewrite of set with $e encoding, $d data" {
r flushall
if {$e eq {intset}} {set len 10} else {set len 1000}
for {set j 0} {$j < $len} {incr j} {
if {$d eq {string}} {
set data [randstring 0 16 alpha]
} else {
set data [randomInt 4000000000]
}
r sadd key $data
}
if {$d ne {string}} {
assert_equal [r object encoding key] $e
}
set d1 [debug_digest]
2011-12-12 09:34:00 -05:00
r bgrewriteaof
waitForBgrewriteaof r
r debug loadaof
set d2 [debug_digest]
2011-12-12 09:34:00 -05:00
if {$d1 ne $d2} {
error "assertion:$d1 is not equal to $d2"
}
}
}
}
foreach d {string int} {
foreach e {listpack hashtable} {
2011-12-12 09:34:00 -05:00
test "AOF rewrite of hash with $e encoding, $d data" {
r flushall
if {$e eq {listpack}} {set len 10} else {set len 1000}
2011-12-12 09:34:00 -05:00
for {set j 0} {$j < $len} {incr j} {
if {$d eq {string}} {
set data [randstring 0 16 alpha]
} else {
set data [randomInt 4000000000]
}
r hset key $data $data
}
assert_equal [r object encoding key] $e
set d1 [debug_digest]
2011-12-12 09:34:00 -05:00
r bgrewriteaof
waitForBgrewriteaof r
r debug loadaof
set d2 [debug_digest]
2011-12-12 09:34:00 -05:00
if {$d1 ne $d2} {
error "assertion:$d1 is not equal to $d2"
}
}
}
}
foreach d {string int} {
Replace all usage of ziplist with listpack for t_zset (#9366) Part two of implementing #8702 (zset), after #8887. ## Description of the feature Replaced all uses of ziplist with listpack in t_zset, and optimized some of the code to optimize performance. ## Rdb format changes New `RDB_TYPE_ZSET_LISTPACK` rdb type. ## Rdb loading improvements: 1) Pre-expansion of dict for validation of duplicate data for listpack and ziplist. 2) Simplifying the release of empty key objects when RDB loading. 3) Unify ziplist and listpack data verify methods for zset and hash, and move code to rdb.c. ## Interface changes 1) New `zset-max-listpack-entries` config is an alias for `zset-max-ziplist-entries` (same with `zset-max-listpack-value`). 2) OBJECT ENCODING will return listpack instead of ziplist. ## Listpack improvements: 1) Add `lpDeleteRange` and `lpDeleteRangeWithEntry` functions to delete a range of entries from listpack. 2) Improve the performance of `lpCompare`, converting from string to integer is faster than converting from integer to string. 3) Replace `snprintf` with `ll2string` to improve performance in converting numbers to strings in `lpGet()`. ## Zset improvements: 1) Improve the performance of `zzlFind` method, use `lpFind` instead of `lpCompare` in a loop. 2) Use `lpDeleteRangeWithEntry` instead of `lpDelete` twice to delete a element of zset. ## Tests 1) Add some unittests for `lpDeleteRange` and `lpDeleteRangeWithEntry` function. 2) Add zset RDB loading test. 3) Add benchmark test for `lpCompare` and `ziplsitCompare`. 4) Add empty listpack zset corrupt dump test.
2021-09-09 11:18:53 -04:00
foreach e {listpack skiplist} {
2011-12-12 09:34:00 -05:00
test "AOF rewrite of zset with $e encoding, $d data" {
r flushall
Replace all usage of ziplist with listpack for t_zset (#9366) Part two of implementing #8702 (zset), after #8887. ## Description of the feature Replaced all uses of ziplist with listpack in t_zset, and optimized some of the code to optimize performance. ## Rdb format changes New `RDB_TYPE_ZSET_LISTPACK` rdb type. ## Rdb loading improvements: 1) Pre-expansion of dict for validation of duplicate data for listpack and ziplist. 2) Simplifying the release of empty key objects when RDB loading. 3) Unify ziplist and listpack data verify methods for zset and hash, and move code to rdb.c. ## Interface changes 1) New `zset-max-listpack-entries` config is an alias for `zset-max-ziplist-entries` (same with `zset-max-listpack-value`). 2) OBJECT ENCODING will return listpack instead of ziplist. ## Listpack improvements: 1) Add `lpDeleteRange` and `lpDeleteRangeWithEntry` functions to delete a range of entries from listpack. 2) Improve the performance of `lpCompare`, converting from string to integer is faster than converting from integer to string. 3) Replace `snprintf` with `ll2string` to improve performance in converting numbers to strings in `lpGet()`. ## Zset improvements: 1) Improve the performance of `zzlFind` method, use `lpFind` instead of `lpCompare` in a loop. 2) Use `lpDeleteRangeWithEntry` instead of `lpDelete` twice to delete a element of zset. ## Tests 1) Add some unittests for `lpDeleteRange` and `lpDeleteRangeWithEntry` function. 2) Add zset RDB loading test. 3) Add benchmark test for `lpCompare` and `ziplsitCompare`. 4) Add empty listpack zset corrupt dump test.
2021-09-09 11:18:53 -04:00
if {$e eq {listpack}} {set len 10} else {set len 1000}
2011-12-12 09:34:00 -05:00
for {set j 0} {$j < $len} {incr j} {
if {$d eq {string}} {
set data [randstring 0 16 alpha]
} else {
set data [randomInt 4000000000]
}
r zadd key [expr rand()] $data
}
assert_equal [r object encoding key] $e
set d1 [debug_digest]
2011-12-12 09:34:00 -05:00
r bgrewriteaof
waitForBgrewriteaof r
r debug loadaof
set d2 [debug_digest]
2011-12-12 09:34:00 -05:00
if {$d1 ne $d2} {
error "assertion:$d1 is not equal to $d2"
}
}
}
}
test "AOF rewrite functions" {
r flushall
r FUNCTION LOAD LUA test DESCRIPTION {desc} {
redis.register_function('test', function() return 1 end)
}
r bgrewriteaof
waitForBgrewriteaof r
r function flush
r debug loadaof
assert_equal [r fcall test 0] 1
r FUNCTION LIST
} {{library_name test engine LUA description desc functions {{name test description {} flags {}}}}}
test {BGREWRITEAOF is delayed if BGSAVE is in progress} {
r flushall
r set k v
r config set rdb-key-save-delay 10000000
r bgsave
assert_match {*scheduled*} [r bgrewriteaof]
assert_equal [s aof_rewrite_scheduled] 1
r config set rdb-key-save-delay 0
catch {exec kill -9 [get_child_pid 0]}
while {[s aof_rewrite_scheduled] eq 1} {
after 100
}
}
test {BGREWRITEAOF is refused if already in progress} {
r config set aof-use-rdb-preamble yes
r config set rdb-key-save-delay 10000000
catch {
r bgrewriteaof
r bgrewriteaof
} e
assert_match {*ERR*already*} $e
r config set rdb-key-save-delay 0
catch {exec kill -9 [get_child_pid 0]}
}
2011-12-12 09:34:00 -05:00
}