live-forum/server/webapi/LiveForum/LiveForum.Code/Redis/RedisService.cs
2026-03-24 11:27:37 +08:00

329 lines
9.0 KiB
C#
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

using LiveForum.Code.Redis.Contract;
using Microsoft.Extensions.Caching.Distributed;
using Microsoft.Extensions.Logging;
using StackExchange.Redis;
using System.Text.Json;
namespace LiveForum.Code
{
/// <summary>
/// Redis缓存服务实现
/// </summary>
public class RedisService : IRedisService
{
private readonly ConnectionMultiplexer _redis;
private readonly ILogger<RedisService> _logger;
public RedisService(ConnectionMultiplexer redis, ILogger<RedisService> logger)
{
_redis = redis;
_logger = logger;
}
private IDatabase Db => _redis.GetDatabase();
public async Task<IDatabase> GetDatabaseAsync()
{
try
{
return await Task.FromResult(Db);
}
catch (Exception ex)
{
_logger.LogError(ex, "获取Redis数据库失败");
throw;
}
}
public async Task SetAsync(string key, string value, TimeSpan? expiration = null)
{
try
{
if (expiration.HasValue)
{
await Db.StringSetAsync(key, value, expiration.Value);
}
else
{
await Db.StringSetAsync(key, value);
}
}
catch (Exception ex)
{
_logger.LogError(ex, "设置Redis缓存失败Key: {Key}", key);
throw;
}
}
public async Task SetAsync<T>(string key, T value, TimeSpan? expiration = null)
{
try
{
var jsonValue = JsonSerializer.Serialize(value);
if (expiration.HasValue)
{
await Db.StringSetAsync(key, jsonValue, expiration.Value);
}
else
{
await Db.StringSetAsync(key, jsonValue);
}
}
catch (Exception ex)
{
_logger.LogError(ex, "设置Redis缓存失败Key: {Key}", key);
throw;
}
}
public async Task<string?> GetAsync(string key)
{
try
{
var value = await Db.StringGetAsync(key);
return value.HasValue ? value.ToString() : null;
}
catch (Exception ex)
{
_logger.LogError(ex, "获取Redis缓存失败Key: {Key}", key);
throw;
}
}
public async Task<T?> GetAsync<T>(string key)
{
try
{
var value = await Db.StringGetAsync(key);
if (!value.HasValue)
{
return default(T);
}
return JsonSerializer.Deserialize<T>(value.ToString());
}
catch (Exception ex)
{
_logger.LogError(ex, "获取Redis缓存失败Key: {Key}", key);
throw;
}
}
public async Task RemoveAsync(string key)
{
try
{
await Db.KeyDeleteAsync(key);
}
catch (Exception ex)
{
_logger.LogError(ex, "删除Redis缓存失败Key: {Key}", key);
throw;
}
}
public async Task<bool> ExistsAsync(string key)
{
try
{
return await Db.KeyExistsAsync(key);
}
catch (Exception ex)
{
_logger.LogError(ex, "检查Redis键是否存在失败Key: {Key}", key);
throw;
}
}
public async Task SetExpirationAsync(string key, TimeSpan expiration)
{
try
{
await Db.KeyExpireAsync(key, expiration);
}
catch (Exception ex)
{
_logger.LogError(ex, "设置Redis键过期时间失败Key: {Key}", key);
throw;
}
}
public async Task<TimeSpan?> GetExpirationAsync(string key)
{
try
{
return await Db.KeyTimeToLiveAsync(key);
}
catch (Exception ex)
{
_logger.LogError(ex, "获取Redis键剩余过期时间失败Key: {Key}", key);
throw;
}
}
public async Task<long> IncrementAsync(string key)
{
try
{
return await Db.StringIncrementAsync(key);
}
catch (Exception ex)
{
_logger.LogError(ex, "Redis自增失败Key: {Key}", key);
throw;
}
}
public async Task<long> DecrementAsync(string key)
{
try
{
return await Db.StringDecrementAsync(key);
}
catch (Exception ex)
{
_logger.LogError(ex, "Redis自减失败Key: {Key}", key);
throw;
}
}
public async Task<long> StringGetInt64Async(string key)
{
try
{
var value = await Db.StringGetAsync(key);
if (!value.HasValue)
{
return 0;
}
if (long.TryParse(value.ToString(), out var result))
{
return result;
}
return 0;
}
catch (Exception ex)
{
_logger.LogError(ex, "获取Redis整数值失败Key: {Key}", key);
throw;
}
}
public async Task<bool> StringSetAsync(string key, long value, TimeSpan? expiration = null)
{
try
{
if (expiration.HasValue)
{
return await Db.StringSetAsync(key, value, expiration.Value);
}
else
{
return await Db.StringSetAsync(key, value);
}
}
catch (Exception ex)
{
_logger.LogError(ex, "设置Redis整数值失败Key: {Key}", key);
throw;
}
}
public async Task<bool> SetAddAsync(string key, RedisValue value)
{
try
{
return await Db.SetAddAsync(key, value);
}
catch (Exception ex)
{
_logger.LogError(ex, "Redis Set添加元素失败Key: {Key}", key);
throw;
}
}
public async Task<bool> SetRemoveAsync(string key, RedisValue value)
{
try
{
return await Db.SetRemoveAsync(key, value);
}
catch (Exception ex)
{
_logger.LogError(ex, "Redis Set移除元素失败Key: {Key}", key);
throw;
}
}
public async Task<bool> SetContainsAsync(string key, RedisValue value)
{
try
{
return await Db.SetContainsAsync(key, value);
}
catch (Exception ex)
{
_logger.LogError(ex, "检查Redis Set是否包含元素失败Key: {Key}", key);
throw;
}
}
public async Task<bool> HashSetAsync(string key, RedisValue field, RedisValue value)
{
try
{
return await Db.HashSetAsync(key, field, value);
}
catch (Exception ex)
{
_logger.LogError(ex, "Redis Hash设置字段失败Key: {Key}, Field: {Field}", key, field);
throw;
}
}
public async Task<RedisValue> HashGetAsync(string key, RedisValue field)
{
try
{
return await Db.HashGetAsync(key, field);
}
catch (Exception ex)
{
_logger.LogError(ex, "Redis Hash获取字段失败Key: {Key}, Field: {Field}", key, field);
throw;
}
}
public async Task<HashEntry[]> HashGetAllAsync(string key)
{
try
{
return await Db.HashGetAllAsync(key);
}
catch (Exception ex)
{
_logger.LogError(ex, "获取Redis Hash所有字段失败Key: {Key}", key);
throw;
}
}
public async Task<bool> HashDeleteAsync(string key, RedisValue field)
{
try
{
return await Db.HashDeleteAsync(key, field);
}
catch (Exception ex)
{
_logger.LogError(ex, "Redis Hash删除字段失败Key: {Key}, Field: {Field}", key, field);
throw;
}
}
}
}