vjzning / redis

Automatically exported from code.google.com/p/redis
https://code.google.com/p/redis/
BSD 3-Clause "New" or "Revised" License
0 stars 0 forks source link

Calling SINTERSTORE/SUNIONSTORE with a volatile key causes volatile key to be destroyed #134

Closed GoogleCodeExporter closed 9 years ago

GoogleCodeExporter commented 9 years ago
What steps will reproduce the problem?

(All command run with without significant delays between)

SINTERSTORE:

>>> r.flush()
'OK'
>>> r.sadd('a', 10)
1
>>> r.sadd('b', 10)
1
>>> r.sinterstore('x', 'a', 'b')
1
>>> r.smembers('x')
set([10])
>>> r.expire('a', 30)
1
>>> r.exists('a')
1
>>> r.sinterstore('x', 'a', 'b')
0
>>> r.smembers('x')
set([])
>>> r.exists('a')
0

Notice that, once we set the key to expire, we then call SINTERSTORE, after 
which 
key 'a' no longer exists

SUNIONSTORE:

>>> r.flush()
'OK'
>>> r.sadd('a', 10)
1
>>> r.sadd('b', 10)
1
>>> r.sunionstore('x', 'a', 'b')
1
>>> r.smembers('x')
set([10])
>>> r.expire('a', 30)
1
>>> r.exists('a')
1
>>> r.sunionstore('x', 'a', 'b')
1
>>> r.smembers('x')
set([10])
>>> r.exists('a')
0

Same result, but key 'x' has a value as we are doing a union rather than an 
intersection (although issue 133 is slightly related here).

What is the expected output? What do you see instead?

The key 'a' should still exist at the end of both of the above examples

What version of the product are you using? On what operating system?

Git master. Ubuntu 9.04 64bit (VM under Parallels on OS X)

Original issue reported on code.google.com by acharnock on 29 Dec 2009 at 3:35

GoogleCodeExporter commented 9 years ago
Hello, this is not a bug. S*STORE commands write to the dataset even if they 
don't write 
against the key, so the delete-on-write policy must be honored here.

Original comment by anti...@gmail.com on 29 Dec 2009 at 3:41

GoogleCodeExporter commented 9 years ago
Hi Antirez, thanks for the fast response. Am I therefore correct in thinking 
that the only 
way to perform a stored intersection on a volatile key is to us SINTER and then 
use 
multiple SADD calls?

Original comment by acharnock on 29 Dec 2009 at 4:12

GoogleCodeExporter commented 9 years ago
Bug or not, please consider supporting this.  This really seems 
counterintuitive - the src 
datasets should never be modified as a result of this operation, so they 
shouldn't cause 
keys to expire.

Original comment by csy...@gmail.com on 15 Feb 2010 at 3:38

GoogleCodeExporter commented 9 years ago
I would second this. I appreciate that there may be internal reasons for this, 
but it does 
seem counterintuitive and would be rather useful in my current project (as we 
do 
searches by using the union/intersection of sets, and we would like the 
temporary keys 
to be stay around for a minute or so as a simple cache).

Thanks!

Adam

Original comment by acharnock on 15 Feb 2010 at 9:08

GoogleCodeExporter commented 9 years ago
This is really counterintuitive and a showstopper for using Redis in order to 
store online users (online users being store in a key from the current minute. 
This is somethinig that has to expire).

Easy way to reproduce this:

redis> sadd test foo
(integer) 1
redis> expire test 10000
(integer) 1
redis> sunion test
1. "foo"
redis> sunionstore bar test
(integer) 0
redis> smembers bar
(empty list or set)

Original comment by chrysa...@gmail.com on 13 Jun 2010 at 1:41

GoogleCodeExporter commented 9 years ago
The same happens when using srem or sadd. In my situation I have a key set to 
expire in 1h, but sometimes I need to remove members from that key which causes 
the whole set to be empty.

To reproduce:

redis> sadd test 1
(integer) 1
redis> sadd test 2
(integer) 1
redis> sadd test 3
(integer) 1
redis> smembers test
1. "3"
2. "1"
3. "2"
redis> expire test 3000
(integer) 1
redis> smembers test
1. "3"
2. "1"
3. "2"
redis> srem test 1
(integer) 0
redis> smembers test
(empty list or set)

Original comment by astri...@gmail.com on 3 Aug 2010 at 8:19

GoogleCodeExporter commented 9 years ago
I forgot to mention that I tested this both on 1.2.6 and 2.0.0-rc4, same 
behaviour

Original comment by astri...@gmail.com on 3 Aug 2010 at 8:21

GoogleCodeExporter commented 9 years ago
Every write operation on expiring keys destroys the target key to avoid 
consistency issues on replication. This is all well-explained here: 
http://code.google.com/p/redis/wiki/ExpireCommand .

This behavior is going to change post 2.0, see: 
http://groups.google.com/group/redis-db/browse_thread/thread/23769aa031304e80?hl
=en# .

Original comment by pcnoordh...@gmail.com on 3 Aug 2010 at 9:15

GoogleCodeExporter commented 9 years ago
all this problems are fixed by Redis 2.2 (currently Redis master) that allows 
writes against volatile keys.

Cheers,
Salvatore

Original comment by anti...@gmail.com on 24 Aug 2010 at 8:12