Я пытаюсь поместить redis вместо существующей системы кэширования, которая в основном состоит из Dictionary<id, class>
. У меня есть около 500 000 объектов, и я использую MsgPackObjectSerializer. Я сталкиваюсь с проблемами производительности при попытке получить весь набор данных.
Получение всех ключей занимает несколько секунд.
var keys = cacheClient.SearchKeys("ID:*").ToList();
и использование метода GetAll следующим образом:
cacheClient.GetAll<class>(keys).Values;
приводит к тайм-ауту даже при следующей конфигурации:
var configOptions = new ConfigurationOptions();
configOptions.EndPoints.Add("localhost:6379");
configOptions.ClientName = "RedisClient";
configOptions.ConnectTimeout = (int) TimeSpan.FromSeconds(5).TotalMilliseconds;
configOptions.SyncTimeout = (int) TimeSpan.FromSeconds(5).TotalMilliseconds;
configOptions.AbortOnConnectFail = false;
configOptions.ResponseTimeout = (int) TimeSpan.FromSeconds(5).TotalMilliseconds;
Единственный способ, которым я смог получить результаты, заключается в следующем:
var fromRedis = new ConcurrentDictionary<id, class>();
keys.AsParallel().ForAll(k =>
{
var div = cacheClient.Get<class>(k);
if (div != null)
{
fromRedis.TryAdd(k, div)
}
});
Что мне не кажется правильным и очень медленное.
Должен быть лучший способ сделать это, которого я не вижу.
Обновление:
Это немного быстрее, чем ключи. Параллельный вызов. Все еще занимает 6 секунд ...
var insListScan = new List<Task<RedisValue[]>>();
foreach (var batch in server.Keys(0, "InstrumentSK:*").Batch(1000))
{
var tran = cacheClient.Database.CreateTransaction();
insListScan.Add(tran.StringGetAsync(batch.ToArray()));
tran.Execute();
}