We are moving our Redis stuff to a more robust setup with a ReplicaSet consisting of 1 master and two slaves.
The ReplicaSet is running on CentOS and working fine, switching slaves to a master etc works fine. Now I need to migrate my existing application code which is currently only supporting ‘standalone’ Redis servers to support the new Redis replica set with sentinel.
Currently I use in my AppHost.Configure()
code like so: (Sorry, don’t know how to escape the ‘$’ in C# code…)
connStrCfg = $"redis://{redisServer}:{redisPort}?ConnectTimeout=5000&Db={BbConsumerConstants.RedisProdDb}&password={HttpUtility.UrlEncode(pwdRedisConfig)}";
var redisCfgPool = new PooledRedisClientManager(connStrCfg);
container.Register(c => new SysConfigRepository(redisCfgPool));
I am reading the Wiki documentation and have a few questions:
The documentation states:
var sentinel = new RedisSentinel(sentinelHosts, masterName: "mymaster");
This is a bit confusing! I guess with masterName
you do not mean the name of the machine which is master but you mean the replica set name? The name of the master can change whenever it goes down and a slave becomes master. How can I now which machine is currently master when I (re-)start my application?? The redis sentinel documentation says:
sentinel monitor mymaster 127.0.0.1 6379 2
# where the meaning is as follows
sentinel monitor <master-group-name> <ip> <port> <quorum>
This is what you have to setup in the senitel.conf
file on Linux. I call master-group-name
‘Redis replica set name’ which indicates a bit more clear what it means. So here is an extract of my sentinel.conf
on CentOS:
sentinel redis-config-rs dbinfra2.tbhome.int 6381 2
sentinel auth-pass redis-config-rs MySuperDuperTopSecretPassword
sentinel down-after-milliseconds redis-config-rs 15000
sentinel parallel-syncs redis-config-rs 1
sentinel failover-timeout redis-config-rs 180000
Where redis-config-rs
is the name of the replica set, a logical name of a group of hosts that make up the replica set (you name this myMaster
). This appears in many of the config settings for sentinel to define to which replica set a value belongs.
So here is some of my ‘migrated’ code to support sentinel: Is this correct???
// replsetname would be "redis-config-rs" from above config file
var sentinel = new RedisSentinel(sentinelHosts, masterName: replSetName);
Other questions
-
I have three nodes in my replica set, apart from the hostname all parameters are the same. Do I have to define three sentinel.HostFilter like so?
sentinel.HostFilter = host1 => $"{host1}?Db={BbConsumerConstants.RedisProdDb}&RetryTimeout=5000&password={HttpUtility.UrlEncode(pwdRedisConfig)}";
sentinel.HostFilter = host2 => $"{host2}?Db={BbConsumerConstants.RedisProdDb}&RetryTimeout=5000&password={HttpUtility.UrlEncode(pwdRedisConfig)}";
sentinel.HostFilter = host3 => $"{host3}?Db={BbConsumerConstants.RedisProdDb}&RetryTimeout=5000&password={HttpUtility.UrlEncode(pwdRedisConfig)}"; -
In the documentation you write that there is a newer Pool class
RedisManagerPool
. What are the differences toPooledRedisClientManager
and should I use the newer one? -
Tricky other configuration properties. Do I need to implement any of these? What is the behavior if the master is rebooted and I try to write something to Redis? Will it simply fail or can I handle it in a way? In my configuration (see above) I configured to wait 15 seconds until a new Master is elected. I guess it is much to long, but the final value I will use depends on many things, also on how I configure the service stack client.
Thanks for some hints on these points.