Hello, I think it would be great to have single command for get and del actions. Can you consider accepting PR with this?
Comment From: itamarhaber
Hello @georgyfarniev
The combo sounds interesting, would you please describe the use case(s) for it? Personally, I did not encounter the need for it.
Also, besides the obvious convenience of having a command for that, have you considered using a MULTI/EXEC transaction or a Lua script?
Comment From: georgyfarniev
@antirez use case is very simple: we issue token that can be used just once. We save it to redis. So when we verify it, we need to delete it immediately. I solved this task with multi (using ioredis), but I just thought it would be great to have atomic command for this purpose.
I saw similar use case implemented in other redis command, like SPOP, but it’s only for set.
Suggested name for new command: GETD, GETDEL.
Comment From: itamarhaber
/me not antirez.
I saw similar use case implemented in other redis command, like SPOP, but it’s only for set.
That's actually a great idea (should be documented in my opinion). You can store the string as a single member in the set, and then GETDEL it with SPOP.
Comment From: georgyfarniev
@itamarhaber apologies, I confused. Set is great idea, but It seems hacky if I need just key/value store, isn’t it? And what should be used as set key in this case, if value will be a single token?
Comment From: itamarhaber
No worries :)
From the initial description, I had understood that you're looking for something like the following:
> SET token:123 data
...
> GETDEL token:123
"data"
> GETDEL token:123
(nil)
If that is the case, a set with a single member is non-intuitive perhaps, but not really that hacky - consider:
> SADD token:123 data
(integer) 1
...
> SPOP token:123
"data"
> SPOP token:123
(nil)
This behaves in the required manner and does not require a new command, although depending on the value's size the memory overhead may be too much (strings OH is about 50 bytes and sets are about 200). That overhead would have been an issue if the pattern was widely and wildly used, but afaik it isn't.
And what should be used as set key in this case, if value will be a single token?
I'm not sure that I'm following this question. If all you have are token IDs that you need to perform an existence check for, you can use a regular set for all of them. Example:
> SADD tokens 1
(integer) 1
...
> SREM tokens 1
(integer) 1
> SREM tokens 1
(integer) 0
As you can see, SREM's reply indicates whether the member was removed (and hence it had existed and wasn't used) or not (and hence it is an invalid, perhaps already used, token).
Comment From: zh1029
Why don't implement an extend redis command via redis module? it is easy to implement without hacking redis core code. and you can implement it by yourself.
Comment From: georgyfarniev
@zh1029 im not very familiar with redis internals. You mean using multi? I already use it in ioredis, but I think it make sense to have this operation as single command since it can be very useful.
Comment From: zh1029
@georgyfarniev, I mean you can implement one redis module to extend redis command. It is very cool and fun redis functionality. https://redis.io/topics/modules-intro. https://redis.io/topics/modules-api-ref.
I see @gkorland implemented it in RedisX. you can take into use. but license need to be checked if it suit to you. https://github.com/RedisLabsModules/RedisX
Comment From: georgyfarniev
@zh1029, thank you for referring this doc, very useful. However, I will prefer to use transaction in my case. I just was thinking that it good thing to have out of the box. Very often record need to be invalidated once it was read.
Comment From: madolson
Related to https://github.com/redis/redis/issues/7324, so closing this and folding the conversation there.