Ori Refael
Ori Refael

Reputation: 3018

C# ServiceStack.Redis SetAll with expire

First, a link to the library: ServiceStack.Redis

now, Im working on some generic cache mechanism which supports, for now, in 4 methods:

Put, Get, PutMany, GetMany

Problem is, whenever I want to insert numerous records, I dont have an option (visible to me) to add an expiration, unlike Put - where I can.

The code is pretty streight forward:

public void PutMany(ICollection<T> items)
{
    TimeSpan expiration = GetExpiration();
    DateTime expire = DateTime.UtcNow.Add(expiration);

    Dictionary<string, CachedItem<T>> dict = new Dictionary<string, CachedItem<T>>();
    foreach (T item in items)
    {
        CachedItem<T> cacheItem = new CachedItem<T>(item, expire);

        if (!dict.ContainsKey(cacheItem.Id))
            dict.Add(cacheItem.Id, cacheItem);
    }

    // Store item in cache
    _client.SetAll(dict);
}

the model CachedItem<T> is mine, just imagine it as some sort of an object.

As you can see, I dont have an option of setting the expiration. Is there a way (besides inserting them 1 by 1 using _client.Set()) to achieve this?

TIA.

P.S

I know I can store all records in a list or an hash, I dont want that all the records will have a single expiration date (wrong, and can cause very serious performance issues whenever they expire)

Upvotes: 1

Views: 2017

Answers (1)

mythz
mythz

Reputation: 143319

Redis does not have any command that will let you set an expiry with a bulk insert nor does any of its Expire commands allow you to apply the expiry to multiple keys.

To avoid an N+1 operation you'll need to queue multiple SET commands in a Redis Transaction or pipeline, setting each entry individually with an expiry, e.g:

using (var trans = Redis.CreateTransaction())
{
    foreach (var entry in dict) 
    {
        trans.QueueCommand(r => r.SetValue(entry.Key, entry.Value, expireIn));
    }

    trans.Commit();
}

Where ServiceStack.Redis will still send the multiple SET operations in a bulk Redis transaction.

Upvotes: 3

Related Questions