Тайм-аут Redis при наличии большого количества ключейC#

Место общения программистов C#
Anonymous
Тайм-аут Redis при наличии большого количества ключей

Сообщение Anonymous »

Мой WebAPI написан с использованием .NET Framework 4.7.2, и я также использую RedisStackChange 2.8.0.
У меня возникла проблема, когда количество ключей в Redis достигло около 7 миллионов. ключи:

StackExchange.Redis.RedisTimeoutException: таймаут выполнения GET (5000 мс), следующий: GET xxx, inst: 15, qu: 0, qs: 3, aw: False, rs: ReadAsync, ws: Idle, вход: 0, входной канал: 0, выходной канал: 132, serverEndpoint: 10.xx.xx.xx:xxxx, mc: 1/1/0, mgr: Доступно 7 из 10, имя клиента: XXXX-XXXX, IOCP: (Занят = 9, Свободен = 991, Мин = 16, Макс = 1000), РАБОЧИЙ: (Занят = 146, Свободен = 32621, Мин = 16, Макс = 32767)

Это приводит к сильному замедлению работы приложения. Чтобы устранить проблему, я увеличил время ожидания с 5 до 30 секунд (Redis и API используют один и тот же сервер – 48 ГБ ОЗУ).
Интересно, есть ли лучший способ справиться с этим?
Я впервые задаю вопрос, спасибо за чтение
Это сокращенная версия моего кода:
public class RedisClient : IDisposable
{
private ConnectionMultiplexer _connection;

public RedisClient()
{
Connect();
}

public void Connect()
{
var configuration = ConfigurationOptions.Parse(ConfigurationManager.AppSettings["REDIS_CONN_STRING"]);
_connection = ConnectionMultiplexer.Connect(configuration);
}

public static RedisClient GetReConnectInstance()
{
if (_redisClient == null)
{
_redisClient = new RedisClient();
}

return _redisClient;
}

private static RedisClient _redisClient;

public static RedisClient GetInstance()
{
if (_redisClient == null)
{
_redisClient = new RedisClient();
}

return _redisClient;
}

public void Dispose()
{
Dispose(true);
GC.SuppressFinalize(this);
}

protected virtual void Dispose(bool disposing)
{
if (disposing)
{
Close();
}

}
}

public class RedisCacheManager
{
private IDatabase _db;
private IMinvoiceDbContext _minvoiceDbContext;

public RedisCacheManager(IMinvoiceDbContext minvoiceDbContext)
{
_minvoiceDbContext = minvoiceDbContext;

try
{
RedisClient redisClient = RedisClient.GetInstance();
_db = redisClient.Database();
}
catch (Exception ex)
{
Log.Error("RedisCacheManager", ex);
ReconnectDB();
}
}

private void ReconnectDB()
{
try
{
RedisClient redisClient = RedisClient.GetReConnectInstance();
_db = redisClient.Database();
}
catch (Exception ex)
{
Log.Error("ReconnectDB", ex);
}

}

public async Task Get(string key)
{
T rs = default(T);

try
{
var rValue = await _db.StringGetAsync(key);

if (!rValue.HasValue)
return default(T);

rs = Deserialize(rValue);
}
catch (RedisConnectionException ex)
{
Log.Error($"Get: {key}", ex);
ReconnectDB();
}
catch (Exception ex)
{
Log.Error("Get", ex);
}
return rs;
}
}

// WHEN I USE REDIS
RedisCacheManager cacheManager = new RedisCacheManager(_minvoiceDbContext);
string old = await cacheManager.Get(CacheKeyManager.CHECK_TAX_CODE_OLD);


Подробнее здесь: https://stackoverflow.com/questions/790 ... er-of-keys

Вернуться в «C#»