Skip to content

Commit 87abee7

Browse files
committed
[fix]: increase bgsave wait timeout for SWAP diskless replicas-drop test && [test]: skip 'rdb child dies when parent killed' in SWAP mode
1 parent 83fdec3 commit 87abee7

3 files changed

Lines changed: 117 additions & 3 deletions

File tree

tests/integration/replication.tcl

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1102,8 +1102,9 @@ test "diskless replication child being killed is collected" {
11021102

11031103
foreach mdl {yes no} {
11041104
test "replication child dies when parent is killed - diskless: $mdl" {
1105+
11051106
# when master is killed, make sure the fork child can detect that and exit
1106-
start_server {tags {"repl"} overrides {save ""}} {
1107+
start_server {tags {"repl" "memonly"} overrides {save ""}} {
11071108
set master [srv 0 client]
11081109
set master_host [srv 0 host]
11091110
set master_port [srv 0 port]

tests/swap/ported/integration/replication.tcl

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -385,8 +385,11 @@ start_server {tags {"repl" "nosanitizer"} overrides {swap-repl-rordb-sync no}} {
385385
after 2000
386386
}
387387

388-
# wait for rdb child to exit
389-
wait_for_condition 500 100 {
388+
# wait for rdb child to exit.
389+
# In SWAP mode the slow replica uses repl-diskless-load swapdb which
390+
# incurs RocksDB write overhead per key (~1-2ms) on top of key-load-delay
391+
# (100us). 20k keys * ~2ms = ~40s, so use a 3-minute ceiling.
392+
wait_for_condition 1800 100 {
390393
[s -2 rdb_bgsave_in_progress] == 0
391394
} else {
392395
fail "rdb child didn't terminate"

tests/swap/unit/expire.tcl

Lines changed: 110 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -139,6 +139,116 @@ start_server {tags "expire"} {
139139
}
140140
}
141141

142+
# Guard tests for scanMetaExpireIfNeeded ordering regression (fixed in dfa99d68a).
143+
# Bug: scanMetaExpireIfNeeded was placed AFTER stringmatchlen / type filters,
144+
# so expired cold keys that didn't match MATCH or TYPE were never deleted.
145+
# These tests must FAIL on pre-fix code and PASS on post-fix code.
146+
start_server {tags "scanMetaExpireIfNeeded"} {
147+
r config set swap-debug-evict-keys 0
148+
149+
test {scanMetaExpireIfNeeded: expired cold keys deleted even when MATCH does not match} {
150+
# Pre-fix: stringmatchlen ran first; non-matching keys skipped before
151+
# scanMetaExpireIfNeeded, so they were never submitted for deletion.
152+
r debug set-active-expire 0
153+
r flushall
154+
155+
foreach key {expire:1 expire:2 expire:3} {
156+
r psetex $key 500 bar
157+
r swap.evict $key
158+
wait_key_cold r $key
159+
}
160+
after 600
161+
162+
# Full scan with a pattern that matches NONE of the expired keys.
163+
set cursor 0
164+
while 1 {
165+
set res [r scan $cursor match other:*]
166+
set cursor [lindex $res 0]
167+
if {$cursor == 0} break
168+
}
169+
170+
# scanMetaExpireIfNeeded must fire regardless of MATCH.
171+
wait_for_condition 100 100 {
172+
[r dbsize] eq 0
173+
} else {
174+
fail "Expired cold keys not deleted when MATCH pattern did not match"
175+
}
176+
foreach key {expire:1 expire:2 expire:3} {
177+
assert_equal [rio_get_meta r $key] {}
178+
}
179+
180+
r debug set-active-expire 1
181+
}
182+
183+
test {scanMetaExpireIfNeeded: expired cold keys deleted even when TYPE filter does not match} {
184+
# Pre-fix: type filter ran first; non-matching keys skipped before
185+
# scanMetaExpireIfNeeded, so they were never submitted for deletion.
186+
r debug set-active-expire 0
187+
r flushall
188+
189+
# String keys will not match TYPE hash.
190+
foreach key {strexp:1 strexp:2 strexp:3} {
191+
r psetex $key 500 bar
192+
r swap.evict $key
193+
wait_key_cold r $key
194+
}
195+
after 600
196+
197+
set cursor 0
198+
while 1 {
199+
set res [r scan $cursor type hash]
200+
set cursor [lindex $res 0]
201+
if {$cursor == 0} break
202+
}
203+
204+
# scanMetaExpireIfNeeded must fire regardless of TYPE filter.
205+
wait_for_condition 100 100 {
206+
[r dbsize] eq 0
207+
} else {
208+
fail "Expired cold keys not deleted when TYPE filter did not match"
209+
}
210+
foreach key {strexp:1 strexp:2 strexp:3} {
211+
assert_equal [rio_get_meta r $key] {}
212+
}
213+
214+
r debug set-active-expire 1
215+
}
216+
217+
test {scanMetaExpireIfNeeded: expired cold keys not matching MATCH are also deleted} {
218+
# Same regression with a mixed key set: some keys match the pattern,
219+
# some do not. Pre-fix: non-matching key (other:99) is never deleted.
220+
r debug set-active-expire 0
221+
r flushall
222+
223+
foreach key {match:1 match:2 other:99} {
224+
r psetex $key 500 bar
225+
r swap.evict $key
226+
wait_key_cold r $key
227+
}
228+
after 600
229+
230+
set cursor 0
231+
while 1 {
232+
set res [r scan $cursor match match:*]
233+
set cursor [lindex $res 0]
234+
assert_equal [llength [lindex $res 1]] 0
235+
if {$cursor == 0} break
236+
}
237+
238+
# All three keys must be deleted, including other:99 which didn't match.
239+
wait_for_condition 100 100 {
240+
[r dbsize] eq 0
241+
} else {
242+
fail "Expired cold key (other:99) not deleted despite MATCH mismatch"
243+
}
244+
foreach key {match:1 match:2 other:99} {
245+
assert_equal [rio_get_meta r $key] {}
246+
}
247+
248+
r debug set-active-expire 1
249+
}
250+
}
251+
142252
start_server {tags "unlink cold string"} {
143253
test {swap out and unlink cold string} {
144254
r set k v

0 commit comments

Comments
 (0)