1start_server {tags {"dump"}} { 2 test {DUMP / RESTORE are able to serialize / unserialize a simple key} { 3 r set foo bar 4 set encoded [r dump foo] 5 r del foo 6 list [r exists foo] [r restore foo 0 $encoded] [r ttl foo] [r get foo] 7 } {0 OK -1 bar} 8 9 test {RESTORE can set an arbitrary expire to the materialized key} { 10 r set foo bar 11 set encoded [r dump foo] 12 r del foo 13 r restore foo 5000 $encoded 14 set ttl [r pttl foo] 15 assert {$ttl >= 3000 && $ttl <= 5000} 16 r get foo 17 } {bar} 18 19 test {RESTORE can set an expire that overflows a 32 bit integer} { 20 r set foo bar 21 set encoded [r dump foo] 22 r del foo 23 r restore foo 2569591501 $encoded 24 set ttl [r pttl foo] 25 assert {$ttl >= (2569591501-3000) && $ttl <= 2569591501} 26 r get foo 27 } {bar} 28 29 test {RESTORE can set an absolute expire} { 30 r set foo bar 31 set encoded [r dump foo] 32 r del foo 33 set now [clock milliseconds] 34 r restore foo [expr $now+3000] $encoded absttl 35 set ttl [r pttl foo] 36 assert {$ttl >= 2900 && $ttl <= 3100} 37 r get foo 38 } {bar} 39 40 test {RESTORE can set LRU} { 41 r set foo bar 42 set encoded [r dump foo] 43 r del foo 44 r config set maxmemory-policy allkeys-lru 45 r restore foo 0 $encoded idletime 1000 46 set idle [r object idletime foo] 47 assert {$idle >= 1000 && $idle <= 1010} 48 r get foo 49 } {bar} 50 51 test {RESTORE can set LFU} { 52 r set foo bar 53 set encoded [r dump foo] 54 r del foo 55 r config set maxmemory-policy allkeys-lfu 56 r restore foo 0 $encoded freq 100 57 set freq [r object freq foo] 58 assert {$freq == 100} 59 r get foo 60 } {bar} 61 62 test {RESTORE returns an error of the key already exists} { 63 r set foo bar 64 set e {} 65 catch {r restore foo 0 "..."} e 66 set e 67 } {*BUSYKEY*} 68 69 test {RESTORE can overwrite an existing key with REPLACE} { 70 r set foo bar1 71 set encoded1 [r dump foo] 72 r set foo bar2 73 set encoded2 [r dump foo] 74 r del foo 75 r restore foo 0 $encoded1 76 r restore foo 0 $encoded2 replace 77 r get foo 78 } {bar2} 79 80 test {RESTORE can detect a syntax error for unrecongized options} { 81 catch {r restore foo 0 "..." invalid-option} e 82 set e 83 } {*syntax*} 84 85 test {DUMP of non existing key returns nil} { 86 r dump nonexisting_key 87 } {} 88 89 test {MIGRATE is caching connections} { 90 # Note, we run this as first test so that the connection cache 91 # is empty. 92 set first [srv 0 client] 93 r set key "Some Value" 94 start_server {tags {"repl"}} { 95 set second [srv 0 client] 96 set second_host [srv 0 host] 97 set second_port [srv 0 port] 98 99 assert_match {*migrate_cached_sockets:0*} [r -1 info] 100 r -1 migrate $second_host $second_port key 9 1000 101 assert_match {*migrate_cached_sockets:1*} [r -1 info] 102 } 103 } 104 105 test {MIGRATE cached connections are released after some time} { 106 after 15000 107 assert_match {*migrate_cached_sockets:0*} [r info] 108 } 109 110 test {MIGRATE is able to migrate a key between two instances} { 111 set first [srv 0 client] 112 r set key "Some Value" 113 start_server {tags {"repl"}} { 114 set second [srv 0 client] 115 set second_host [srv 0 host] 116 set second_port [srv 0 port] 117 118 assert {[$first exists key] == 1} 119 assert {[$second exists key] == 0} 120 set ret [r -1 migrate $second_host $second_port key 9 5000] 121 assert {$ret eq {OK}} 122 assert {[$first exists key] == 0} 123 assert {[$second exists key] == 1} 124 assert {[$second get key] eq {Some Value}} 125 assert {[$second ttl key] == -1} 126 } 127 } 128 129 test {MIGRATE is able to copy a key between two instances} { 130 set first [srv 0 client] 131 r del list 132 r lpush list a b c d 133 start_server {tags {"repl"}} { 134 set second [srv 0 client] 135 set second_host [srv 0 host] 136 set second_port [srv 0 port] 137 138 assert {[$first exists list] == 1} 139 assert {[$second exists list] == 0} 140 set ret [r -1 migrate $second_host $second_port list 9 5000 copy] 141 assert {$ret eq {OK}} 142 assert {[$first exists list] == 1} 143 assert {[$second exists list] == 1} 144 assert {[$first lrange list 0 -1] eq [$second lrange list 0 -1]} 145 } 146 } 147 148 test {MIGRATE will not overwrite existing keys, unless REPLACE is used} { 149 set first [srv 0 client] 150 r del list 151 r lpush list a b c d 152 start_server {tags {"repl"}} { 153 set second [srv 0 client] 154 set second_host [srv 0 host] 155 set second_port [srv 0 port] 156 157 assert {[$first exists list] == 1} 158 assert {[$second exists list] == 0} 159 $second set list somevalue 160 catch {r -1 migrate $second_host $second_port list 9 5000 copy} e 161 assert_match {ERR*} $e 162 set res [r -1 migrate $second_host $second_port list 9 5000 copy replace] 163 assert {$ret eq {OK}} 164 assert {[$first exists list] == 1} 165 assert {[$second exists list] == 1} 166 assert {[$first lrange list 0 -1] eq [$second lrange list 0 -1]} 167 } 168 } 169 170 test {MIGRATE propagates TTL correctly} { 171 set first [srv 0 client] 172 r set key "Some Value" 173 start_server {tags {"repl"}} { 174 set second [srv 0 client] 175 set second_host [srv 0 host] 176 set second_port [srv 0 port] 177 178 assert {[$first exists key] == 1} 179 assert {[$second exists key] == 0} 180 $first expire key 10 181 set ret [r -1 migrate $second_host $second_port key 9 5000] 182 assert {$ret eq {OK}} 183 assert {[$first exists key] == 0} 184 assert {[$second exists key] == 1} 185 assert {[$second get key] eq {Some Value}} 186 assert {[$second ttl key] >= 7 && [$second ttl key] <= 10} 187 } 188 } 189 190 test {MIGRATE can correctly transfer large values} { 191 set first [srv 0 client] 192 r del key 193 for {set j 0} {$j < 40000} {incr j} { 194 r rpush key 1 2 3 4 5 6 7 8 9 10 195 r rpush key "item 1" "item 2" "item 3" "item 4" "item 5" \ 196 "item 6" "item 7" "item 8" "item 9" "item 10" 197 } 198 assert {[string length [r dump key]] > (1024*64)} 199 start_server {tags {"repl"}} { 200 set second [srv 0 client] 201 set second_host [srv 0 host] 202 set second_port [srv 0 port] 203 204 assert {[$first exists key] == 1} 205 assert {[$second exists key] == 0} 206 set ret [r -1 migrate $second_host $second_port key 9 10000] 207 assert {$ret eq {OK}} 208 assert {[$first exists key] == 0} 209 assert {[$second exists key] == 1} 210 assert {[$second ttl key] == -1} 211 assert {[$second llen key] == 40000*20} 212 } 213 } 214 215 test {MIGRATE can correctly transfer hashes} { 216 set first [srv 0 client] 217 r del key 218 r hmset key field1 "item 1" field2 "item 2" field3 "item 3" \ 219 field4 "item 4" field5 "item 5" field6 "item 6" 220 start_server {tags {"repl"}} { 221 set second [srv 0 client] 222 set second_host [srv 0 host] 223 set second_port [srv 0 port] 224 225 assert {[$first exists key] == 1} 226 assert {[$second exists key] == 0} 227 set ret [r -1 migrate $second_host $second_port key 9 10000] 228 assert {$ret eq {OK}} 229 assert {[$first exists key] == 0} 230 assert {[$second exists key] == 1} 231 assert {[$second ttl key] == -1} 232 } 233 } 234 235 test {MIGRATE timeout actually works} { 236 set first [srv 0 client] 237 r set key "Some Value" 238 start_server {tags {"repl"}} { 239 set second [srv 0 client] 240 set second_host [srv 0 host] 241 set second_port [srv 0 port] 242 243 assert {[$first exists key] == 1} 244 assert {[$second exists key] == 0} 245 246 set rd [redis_deferring_client] 247 $rd debug sleep 1.0 ; # Make second server unable to reply. 248 set e {} 249 catch {r -1 migrate $second_host $second_port key 9 500} e 250 assert_match {IOERR*} $e 251 } 252 } 253 254 test {MIGRATE can migrate multiple keys at once} { 255 set first [srv 0 client] 256 r set key1 "v1" 257 r set key2 "v2" 258 r set key3 "v3" 259 start_server {tags {"repl"}} { 260 set second [srv 0 client] 261 set second_host [srv 0 host] 262 set second_port [srv 0 port] 263 264 assert {[$first exists key1] == 1} 265 assert {[$second exists key1] == 0} 266 set ret [r -1 migrate $second_host $second_port "" 9 5000 keys key1 key2 key3] 267 assert {$ret eq {OK}} 268 assert {[$first exists key1] == 0} 269 assert {[$first exists key2] == 0} 270 assert {[$first exists key3] == 0} 271 assert {[$second get key1] eq {v1}} 272 assert {[$second get key2] eq {v2}} 273 assert {[$second get key3] eq {v3}} 274 } 275 } 276 277 test {MIGRATE with multiple keys must have empty key arg} { 278 catch {r MIGRATE 127.0.0.1 6379 NotEmpty 9 5000 keys a b c} e 279 set e 280 } {*empty string*} 281 282 test {MIGRATE with multiple keys migrate just existing ones} { 283 set first [srv 0 client] 284 r set key1 "v1" 285 r set key2 "v2" 286 r set key3 "v3" 287 start_server {tags {"repl"}} { 288 set second [srv 0 client] 289 set second_host [srv 0 host] 290 set second_port [srv 0 port] 291 292 set ret [r -1 migrate $second_host $second_port "" 9 5000 keys nokey-1 nokey-2 nokey-2] 293 assert {$ret eq {NOKEY}} 294 295 assert {[$first exists key1] == 1} 296 assert {[$second exists key1] == 0} 297 set ret [r -1 migrate $second_host $second_port "" 9 5000 keys nokey-1 key1 nokey-2 key2 nokey-3 key3] 298 assert {$ret eq {OK}} 299 assert {[$first exists key1] == 0} 300 assert {[$first exists key2] == 0} 301 assert {[$first exists key3] == 0} 302 assert {[$second get key1] eq {v1}} 303 assert {[$second get key2] eq {v2}} 304 assert {[$second get key3] eq {v3}} 305 } 306 } 307 308 test {MIGRATE with multiple keys: stress command rewriting} { 309 set first [srv 0 client] 310 r flushdb 311 r mset a 1 b 2 c 3 d 4 c 5 e 6 f 7 g 8 h 9 i 10 l 11 m 12 n 13 o 14 p 15 q 16 312 start_server {tags {"repl"}} { 313 set second [srv 0 client] 314 set second_host [srv 0 host] 315 set second_port [srv 0 port] 316 317 set ret [r -1 migrate $second_host $second_port "" 9 5000 keys a b c d e f g h i l m n o p q] 318 319 assert {[$first dbsize] == 0} 320 assert {[$second dbsize] == 15} 321 } 322 } 323 324 test {MIGRATE with multiple keys: delete just ack keys} { 325 set first [srv 0 client] 326 r flushdb 327 r mset a 1 b 2 c 3 d 4 c 5 e 6 f 7 g 8 h 9 i 10 l 11 m 12 n 13 o 14 p 15 q 16 328 start_server {tags {"repl"}} { 329 set second [srv 0 client] 330 set second_host [srv 0 host] 331 set second_port [srv 0 port] 332 333 $second mset c _ d _; # Two busy keys and no REPLACE used 334 335 catch {r -1 migrate $second_host $second_port "" 9 5000 keys a b c d e f g h i l m n o p q} e 336 337 assert {[$first dbsize] == 2} 338 assert {[$second dbsize] == 15} 339 assert {[$first exists c] == 1} 340 assert {[$first exists d] == 1} 341 } 342 } 343 344 test {MIGRATE AUTH: correct and wrong password cases} { 345 set first [srv 0 client] 346 r del list 347 r lpush list a b c d 348 start_server {tags {"repl"}} { 349 set second [srv 0 client] 350 set second_host [srv 0 host] 351 set second_port [srv 0 port] 352 $second config set requirepass foobar 353 $second auth foobar 354 355 assert {[$first exists list] == 1} 356 assert {[$second exists list] == 0} 357 set ret [r -1 migrate $second_host $second_port list 9 5000 AUTH foobar] 358 assert {$ret eq {OK}} 359 assert {[$second exists list] == 1} 360 assert {[$second lrange list 0 -1] eq {d c b a}} 361 362 r -1 lpush list a b c d 363 $second config set requirepass foobar2 364 catch {r -1 migrate $second_host $second_port list 9 5000 AUTH foobar} err 365 assert_match {*invalid password*} $err 366 } 367 } 368} 369