Increment / decrement flow with StackExchange.Redis
I am using the StackExchange.Redis package as a shared storage for a multi-threaded application, which in turn will run on multiple servers at the same time ... so multi-threaded;)
One of the simplest use cases I have is that I want to keep the base count on a series of keys (i.e. KEY1 = 4 KEY2 = 7, KEY3 = 13, etc.). And I will have business rules to enforce the maximum allowed value for a given key. For example, say KEY1 can reach 5 ... if two threads fire at exactly the same time trying to increase it, I only want one of them to succeed.
I believe I can accomplish this with a transaction by fetching the current value first, and then making it a condition so that the value doesn't change. Will this work as I expect? Is there a more elegant way to do this?
public void Increment(string key) {
IDatabase db = redisConn.GetDatabase();
var val = db.StringGet(key);
int maxVal = 5;
if (Convert.ToInt32(val) < maxVal) {
var trans = db.CreateTransaction();
trans.AddCondition(Condition.StringEqual(key, val));
trans.StringIncrementAsync(key);
trans.Execute();
}
}
PS: Love this package, nice to work with
source to share
Yes, that should work fine. But it is easier and more efficient to use a Lua script via ScriptEvaluate
.
Note: with your current code, you can check the response Execute
and "redo from start" if false
. If on going from 2 to 3 there is a mailing thread with your current code: the update will be discarded. This is not a Lua script issue.
source to share