![]() |
VOOZH | about |
dotnet add package Galosys.Foundation.FreeRedis --version 26.5.20.1
NuGet\Install-Package Galosys.Foundation.FreeRedis -Version 26.5.20.1
<PackageReference Include="Galosys.Foundation.FreeRedis" Version="26.5.20.1" />
<PackageVersion Include="Galosys.Foundation.FreeRedis" Version="26.5.20.1" />Directory.Packages.props
<PackageReference Include="Galosys.Foundation.FreeRedis" />Project file
paket add Galosys.Foundation.FreeRedis --version 26.5.20.1
#r "nuget: Galosys.Foundation.FreeRedis, 26.5.20.1"
#:package Galosys.Foundation.FreeRedis@26.5.20.1
#addin nuget:?package=Galosys.Foundation.FreeRedis&version=26.5.20.1Install as a Cake Addin
#tool nuget:?package=Galosys.Foundation.FreeRedis&version=26.5.20.1Install as a Cake Tool
成熟度: 🟢 稳定 — 生产可用,活跃维护
Galosys.Foundation.FreeRedis 基于 FreeRedis 提供 IRedisConnection 和 RedisTemplate 的完整实现,支持集群、哨兵、分布式锁、幂等性、Pub/Sub、消息队列、缓存管理等场景。
ResilientRedisConnection 装饰器,指数退避 + 随机抖动自动重试FreeRedisMessageListenerContainer 托管服务,自动管理订阅生命周期FreeRedisDistributedLock 实现,Lua 原子脚本 + 看门狗自动续期FreeRedisDistributedIdempotence 实现,原子标记 + 结果缓存IDistributedCache + RedisCacheManager 命名缓存管理RedisHealthCheck 自动注册,PING 延迟监测RedisConnectionLogger 自动记录连接事件dotnet add package Galosys.Foundation.FreeRedis
从 appsettings.json 的 ConnectionStrings:Redis 读取:
{
"ConnectionStrings": {
"Redis": "localhost:6379,abortConnect=false" // 单节点连接字符串
}
}
使用结构化配置节,支持哨兵、密码、超时、重试等完整参数:
{
"Redis": {
"Connection": {
"ConnectionString": "localhost:6379,abortConnect=false", // 连接字符串(支持集群逗号分隔)
"ServiceName": "mymaster", // Sentinel 主服务名(哨兵模式必填)
"Password": "", // 认证密码(留空表示无密码)
"ConnectTimeout": 5000, // 连接超时(毫秒)
"SyncTimeout": 5000, // 同步操作超时(毫秒)
"AsyncTimeout": 10000, // 异步操作超时(毫秒)
"AbortOnConnectFail": false, // 连接失败时不中止启动
"ConnectRetry": 3, // 初始连接重试次数
"KeepAlive": 60, // TCP KeepAlive 间隔(秒)
"Retry": {
"MaxRetries": 3, // 命令级最大重试次数
"InitialDelayMs": 200, // 首次重试延迟(毫秒)
"MaxDelayMs": 3000, // 最大重试延迟(毫秒)
"EnableJitter": true // 启用随机抖动避免惊群
}
}
}
}
配置优先级:
Redis:Connection节 >ConnectionStrings:Redis(向后兼容)
// 最小化注册 — 自动读取配置并注册所有服务
services.AddRedisClient();
public class OrderService
{
private readonly RedisTemplate _redis;
public OrderService(RedisTemplate redis)
{
_redis = redis;
}
public async Task CreateOrderAsync(Order order)
{
// Value 操作
await _redis.OpsForValue().SetAsync($"order:{order.OrderNo}", order, TimeSpan.FromMinutes(30));
// Hash 操作
await _redis.OpsForHash().PutAsync($"order:detail:{order.OrderNo}", "status", "Created");
// 通用操作
await _redis.ExpireAsync($"order:{order.OrderNo}", TimeSpan.FromHours(24));
}
}
public class RawRedisService
{
private readonly IRedisConnection _connection;
public RawRedisService(IRedisConnection connection)
{
_connection = connection;
}
public async Task<byte[]> GetRawAsync(string key)
{
return await _connection.StringGetAsync(Encoding.UTF8.GetBytes(key));
}
}
基于 Lua 原子脚本实现,支持 await using 自动释放和看门狗自动续期:
public class PaymentService(IDistributedLock @lock)
{
public async Task PayAsync(string orderNo)
{
// await using 自动释放,renewalInterval 启用看门狗自动续期
await using var handle = await @lock.TryAcquireAsync(
$"lock:pay:{orderNo}",
expiry: TimeSpan.FromSeconds(30), // 锁过期时间
waitTimeout: TimeSpan.FromSeconds(5), // 等待获取锁的超时
renewalInterval: TimeSpan.FromSeconds(10)); // 看门狗续期间隔
if (!handle.IsAcquired)
throw new BusinessException("获取锁失败");
// 业务逻辑...
}
}
旧版
TryAcquireAsync(key, expiry)+ReleaseAsync(key)已标记[Obsolete],请迁移至IDistributedLockHandle模式。
基于 Redis 原子操作实现请求幂等性保证,支持结果缓存:
public class OrderService(IDistributedIdempotence idempotence)
{
public async Task<OrderResult> CreateOrderAsync(string requestId, Order order)
{
// 原子标记为处理中,防止重复执行
if (!await idempotence.TryMarkProcessingAsync(requestId, TimeSpan.FromMinutes(10)))
{
// 已有请求在处理,尝试获取缓存结果
var cached = await idempotence.GetCachedResultAsync(requestId);
if (cached != null) return JsonSerializer.Deserialize<OrderResult>(cached);
throw new BusinessException("请求正在处理中");
}
try
{
var result = await DoCreateOrderAsync(order);
// 成功后缓存结果
await idempotence.MarkSuccessAsync(requestId, JsonSerializer.Serialize(result), TimeSpan.FromHours(24));
return result;
}
catch
{
// 失败时清理状态,允许重试
await idempotence.ClearStateAsync(requestId);
throw;
}
}
}
基于 IRedisMessageListenerContainer 实现发布/订阅,自动作为 BackgroundService 管理订阅生命周期。
await redisTemplate.ConvertAndSendAsync("order.events", new OrderEvent { OrderNo = "001" });
// 实现 IMessageListener 接口
public class OrderEventListener : IMessageListener
{
public async Task OnMessageAsync(RedisMessage message)
{
Console.WriteLine($"Channel={message.Channel}, Body={Encoding.UTF8.GetString(message.Body)}");
}
}
// 注册监听器(IRedisMessageListenerContainer 由 DI 自动注册为 HostedService)
var container = serviceProvider.GetRequiredService<IRedisMessageListenerContainer>();
container.AddMessageListener(new OrderEventListener(), "order.events");
基于 Redis Stream 的消息队列,支持延迟投递:
// 发送消息(支持延迟投递)
public class OrderCreatedMessage : IMessage
{
public string OrderNo { get; set; }
public decimal Amount { get; set; }
}
var template = serviceProvider.GetRequiredService<RedisTemplate>();
// 延迟 30 秒投递
await ((FreeRedisTemplate)template).SendAsync("order.created", new OrderCreatedMessage
{
OrderNo = "ORDER001",
Amount = 100.0
}, delaySeconds: 30);
// 处理消息
template.Handle<OrderCreatedMessage>(async msg =>
{
Console.WriteLine($"处理订单: {msg.OrderNo}");
return true;
}, "order.created");
Handle 方法已重构:
CancellationToken 参数,支持优雅关闭CancellationTokenSource,由调用方控制生命周期fieldValues 索引越界问题对标 Spring CacheManager 的命名缓存管理器:
// 注册(在 AddRedisClient 之后)
services.AddRedisCacheManager();
// 使用 Builder 自定义配置
services.AddRedisCacheManager(config =>
{
config.EntryTtl = TimeSpan.FromHours(1); // 默认过期时间
config.KeyPrefix = "myapp:"; // Key 前缀
config.DisableCachingNullValues = false; // 是否禁用缓存 null 值
});
var manager = serviceProvider.GetRequiredService<RedisCacheManager>();
var cache = manager.GetCache("orders"); // 获取或创建命名缓存
await cache.PutAsync("order:001", orderData, TimeSpan.FromHours(1));
var data = await cache.GetAsync<Order>("order:001");
await cache.EvictAsync("order:001"); // 逐出指定 key
await cache.ClearAsync(); // 清空缓存
ResilientRedisConnection 装饰器自动包装所有 Redis 操作,提供透明重试:
InitialDelayMs × 2^(attempt-1) 递增,不超过 MaxDelayMsTimeoutException 及名称包含 Connection / Timeout 的异常Redis:Connection:Retry 节配置,默认 3 次重试
IRedisConnection实际注册为ResilientRedisConnection(FreeRedisConnection),调用方无感知。
RedisHealthCheck 由 AddRedisClient() 自动注册,无需额外配置:
通过 ASP.NET Core 健康检查端点访问:
app.MapHealthChecks("/health");
await _redis.ExecuteInPipelineAsync(pipe =>
{
pipe.SetString("key1"u8.ToArray(), "value1"u8.ToArray());
pipe.SetString("key2"u8.ToArray(), "value2"u8.ToArray());
pipe.SetHash("hash1"u8.ToArray(), "field1"u8.ToArray(), "val"u8.ToArray());
});
| 类 | 说明 |
|---|---|
FreeRedisConnection |
IRedisConnection 实现,封装 FreeRedis RedisClient |
FreeRedisPipeline |
IPipeline 实现,基于 FreeRedis Pipeline |
FreeRedisTemplate |
RedisTemplate 子类,额外支持 Stream 消息队列 SendAsync/Handle |
FreeRedisDistributedLock |
分布式锁实现,Lua 原子脚本 + 看门狗自动续期 |
FreeRedisDistributedIdempotence |
幂等性保证实现,原子标记 + 结果缓存 |
FreeRedisMessageListenerContainer |
Pub/Sub 消息监听容器,继承 BackgroundService |
FreeRedisConnectionLoggerExtensions |
连接事件日志扩展,附加 FreeRedis Notice 事件 |
FreeRedisScriptExecutor |
Lua 脚本执行器,EVALSHA 缓存 + NOSCRIPT fallback |
FreeRedisCli |
[Obsolete] 旧版客户端,保持兼容 |
AddRedisClient() 注册以下服务:
| 服务 | 实现 | 生命周期 |
|---|---|---|
RedisClient (FreeRedis) |
从配置创建 | Singleton |
RedisConnectionLogger |
连接事件日志记录器 | Singleton |
IRedisConnection |
ResilientRedisConnection(FreeRedisConnection) |
Singleton |
RedisTemplate |
FreeRedisTemplate |
Singleton |
IDistributedCache |
FreeRedis DistributedCache | Singleton |
IDistributedLock |
FreeRedisDistributedLock |
Singleton |
IDistributedIdempotence |
FreeRedisDistributedIdempotence |
Singleton |
RedisHealthCheck |
Redis 健康检查 | Singleton |
可选注册(需显式调用):
| 服务 | 实现 | 生命周期 |
|---|---|---|
RedisCacheManager |
命名缓存管理器 | Singleton(AddRedisCacheManager()) |
IRedisMessageListenerContainer |
FreeRedisMessageListenerContainer |
Singleton HostedService |
IRedisScriptExecutor |
FreeRedisScriptExecutor |
Singleton |
IRedisRepository<TEntity, TKey> |
RedisRepository<TEntity, TKey> |
Scoped(AddRedisRepository<T, K>()) |
| Product | Versions Compatible and additional computed target framework versions. |
|---|---|
| .NET | net8.0 net8.0 is compatible. net8.0-android net8.0-android was computed. net8.0-browser net8.0-browser was computed. net8.0-ios net8.0-ios was computed. net8.0-maccatalyst net8.0-maccatalyst was computed. net8.0-macos net8.0-macos was computed. net8.0-tvos net8.0-tvos was computed. net8.0-windows net8.0-windows was computed. net9.0 net9.0 was computed. net9.0-android net9.0-android was computed. net9.0-browser net9.0-browser was computed. net9.0-ios net9.0-ios was computed. net9.0-maccatalyst net9.0-maccatalyst was computed. net9.0-macos net9.0-macos was computed. net9.0-tvos net9.0-tvos was computed. net9.0-windows net9.0-windows was computed. net10.0 net10.0 was computed. net10.0-android net10.0-android was computed. net10.0-browser net10.0-browser was computed. net10.0-ios net10.0-ios was computed. net10.0-maccatalyst net10.0-maccatalyst was computed. net10.0-macos net10.0-macos was computed. net10.0-tvos net10.0-tvos was computed. net10.0-windows net10.0-windows was computed. |
Showing the top 2 NuGet packages that depend on Galosys.Foundation.FreeRedis:
| Package | Downloads |
|---|---|
|
Galosys.Foundation.AspNetCore.DataProtection.FreeRedis
Galosys.Foundation快速开发库 |
|
|
Galosys.NETCore.Base
Galosys.Foundation快速开发库 |
This package is not used by any popular GitHub repositories.
| Version | Downloads | Last Updated |
|---|---|---|
| 26.5.20.1 | 116 | 5/20/2026 |
| 26.5.19.1 | 119 | 5/19/2026 |
| 26.5.18.1 | 111 | 5/18/2026 |
| 26.5.15.1 | 116 | 5/15/2026 |
| 26.5.12.3 | 110 | 5/12/2026 |
| 26.5.12.2 | 111 | 5/12/2026 |
| 26.4.27.1-rc1 | 115 | 4/26/2026 |
| 26.4.25.1-rc1 | 106 | 4/25/2026 |
| 26.4.22.2-rc7 | 116 | 4/22/2026 |
| 26.4.22.2-rc6 | 113 | 4/22/2026 |
| 26.4.22.2-rc4 | 106 | 4/22/2026 |
| 26.4.12.8-rc1 | 133 | 4/12/2026 |
| 26.4.12.7-rc1 | 127 | 4/12/2026 |
| 26.1.30.1-rc1 | 156 | 1/30/2026 |
| 26.1.29.1 | 153 | 1/29/2026 |
| 26.1.28.5 | 144 | 1/28/2026 |
| 26.1.28.4 | 146 | 1/28/2026 |
| 26.1.28.2 | 149 | 1/28/2026 |
| 26.1.23.6 | 152 | 1/23/2026 |
| 26.1.21.1 | 151 | 1/21/2026 |