【发布时间】:2026-02-02 10:00:01
【问题描述】:
我有一个有 3 个节点的 Redis 集群; 1个是master,另外2个是slave,持有master的replica。当我杀死主实例时,Redis Sentinel 将另一个节点提升为主实例,它开始接受写入。
在我的测试中,我注意到一旦新的 master 被提升,使用 SE.Redis 在 Redis 中的第一个操作失败:
StackExchange.Redis.RedisConnectionException:GET 上的 SocketFailure ---> System.IO.IOException: Unable to read data from the transport connection: 现有连接被远程强制关闭 主持人。 ---> System.Net.Sockets.SocketException:现有连接 被远程主机强行关闭
为避免这种情况,我实现了如下重试逻辑。有没有更好的选择?
private RedisValue RedisGet(string key)
{
return RedisOperation(() =>
{
RedisKey redisKey = key;
RedisValue redisValue = connection.StringGet(redisKey);
return (redisValue);
});
}
private T RedisOperation<T>(Func<T> act)
{
int timeToSleepBeforeRetryInMiliseconds = 20;
DateTime startTime = DateTime.Now;
while (true)
{
try
{
return act();
}
catch (Exception e)
{
Debug.WriteLine("Failed to perform REDIS OP");
TimeSpan passedTime = DateTime.Now - startTime;
if (this.retryTimeout < passedTime)
{
Debug.WriteLine("ABORTING re-try to REDIS OP");
throw;
}
else
{
int remainingTimeout = (int)(this.retryTimeout.TotalMilliseconds - passedTime.TotalMilliseconds);
// if remaining time is less than 1 sec than wait only for that much time and than give a last try
if (remainingTimeout < timeToSleepBeforeRetryInMiliseconds)
{
timeToSleepBeforeRetryInMiliseconds = remainingTimeout;
}
}
Debug.WriteLine("Sleeping " + timeToSleepBeforeRetryInMiliseconds + " before next try");
System.Threading.Thread.Sleep(timeToSleepBeforeRetryInMiliseconds);
}
}
}
【问题讨论】: