using StackExchange.Redis; namespace HardwarePerformance.Infrastructure.Services; public interface IRedisCacheService { Task GetAsync(string key); Task SetAsync(string key, T value, TimeSpan? expiry = null); Task RemoveAsync(string key); Task ExistsAsync(string key); Task RemoveByPatternAsync(string pattern); } public class RedisCacheService : IRedisCacheService { private readonly IDatabase _database; private readonly ILogger _logger; public RedisCacheService(IConnectionMultiplexer connectionMultiplexer, ILogger logger) { _database = connectionMultiplexer.GetDatabase(); _logger = logger; } public async Task GetAsync(string key) { try { var value = await _database.StringGetAsync(key); if (value.HasValue) { return JsonSerializer.Deserialize(value!); } return default; } catch (Exception ex) { _logger.LogError(ex, "Error getting value from Redis with key: {Key}", key); return default; } } public async Task SetAsync(string key, T value, TimeSpan? expiry = null) { try { var serializedValue = JsonSerializer.Serialize(value); await _database.StringSetAsync(key, serializedValue, expiry); } catch (Exception ex) { _logger.LogError(ex, "Error setting value to Redis with key: {Key}", key); } } public async Task RemoveAsync(string key) { try { await _database.KeyDeleteAsync(key); } catch (Exception ex) { _logger.LogError(ex, "Error removing key from Redis: {Key}", key); } } public async Task ExistsAsync(string key) { try { return await _database.KeyExistsAsync(key); } catch (Exception ex) { _logger.LogError(ex, "Error checking if key exists in Redis: {Key}", key); return false; } } public async Task RemoveByPatternAsync(string pattern) { try { var server = _database.Multiplexer.GetServer(_database.Multiplexer.GetEndPoints().First()); var keys = server.Keys(database: _database.Database, pattern: pattern); foreach (var key in keys) { await _database.KeyDeleteAsync(key); } } catch (Exception ex) { _logger.LogError(ex, "Error removing keys by pattern from Redis: {Pattern}", pattern); } } }