Welcome to OStack Knowledge Sharing Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
543 views
in Technique[技术] by (71.8m points)

caching - Why are connections to Azure Redis Cache so high?

I am using the Azure Redis Cache in a scenario of high load for a single machine querying the cache. This machine roughly gets and sets about 20 items per second. During daytime this increases, during nighttime this is less.

So far, things have been working fine. Today I realized that the metric of "Connected Clients" is extremely high, although I only have 1 client that just constantly Gets and Sets items. Here is a screenshot of the metric I mean: Redis Cache Connected Clients

My code looks like this:

public class RedisCache<TValue> : ICache<TValue>
{
    private IDatabase cache;
    private ConnectionMultiplexer connectionMultiplexer;

    public RedisCache()
    {
        ConfigurationOptions config = new ConfigurationOptions();
        config.EndPoints.Add(GlobalConfig.Instance.GetConfig("RedisCacheUrl"));
        config.Password = GlobalConfig.Instance.GetConfig("RedisCachePassword");
        config.ConnectRetry = int.MaxValue; // retry connection if broken
        config.KeepAlive = 60; // keep connection alive (ping every minute)
        config.Ssl = true;
        config.SyncTimeout = 8000; // 8 seconds timeout for each get/set/remove operation
        config.ConnectTimeout = 20000; // 20 seconds to connect to the cache

        connectionMultiplexer = ConnectionMultiplexer.Connect(config);
        cache = connectionMultiplexer.GetDatabase();
    }

    public virtual bool Add(string key, TValue item)
    {
        return cache.StringSet(key, RawSerializationHelper.Serialize(item));
    }

I am not creating more than one instance of this class, so this is not the problem. Maybe I missunderstand the connections metric and what they really mean is the number of times I access the cache, however, it would not really make sense in my opinion. Any ideas, or anyone with a similar problem?

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Answer

0 votes
by (71.8m points)

StackExchange.Redis had a race condition that could lead to leaked connections under some conditions. This has been fixed in build 1.0.333 or newer.

If you want to confirm this is the issue you are hitting, get a crash dump of your client application and look at the objects on the heap in a debugger. Look for a large number of StackExchange.Redis.ServerEndPoint objects.

Also, several users have had a bugs in their code that resulted in leaked connection objects. This is often because their code is trying to re-create the ConnectionMultiplexer object if they see failures or disconnected state. There is really no need to recreate the ConnectionMultiplexer as it has logic internally to recreate the connection as necessary. Just make sure to set abortConnect to false in your connection string.

If you do decide to re-create the connection object, make sure to dispose the old object before releasing all references to it.

The following is the pattern we are recommending:


        private static Lazy lazyConnection = new Lazy(() => {
            return ConnectionMultiplexer.Connect("contoso5.redis.cache.windows.net,abortConnect=false,ssl=true,password=...");
        });

        public static ConnectionMultiplexer Connection {
            get {
                return lazyConnection.Value;
            }
        }

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome to OStack Knowledge Sharing Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...