Redis Caching
When your application grows beyond a single server, Redis is the gold standard for distributed caching. It’s fast, scalable, and accessible from anywhere—perfect for microservices, cloud deployments, and high-availability scenarios.
REN.Kit.CacheKit makes using Redis cache in your .NET 8 or .NET 9 projects not only straightforward, but enterprise-ready. You get high performance, reliability, and all the power of Redis, with a developer-friendly interface.
1. Configuration: Define Redis Settings in appsettings.json
Before using Redis, add the following configuration block to your appsettings.json:
"CacheConfiguration": {
"RedisConfiguration": {
"Url": "localhost:6379",
"TimeConfiguration": {
"AbsoluteExpirationInHours": 12
},
"DatabaseId": 4,
"Username": "default",
"Password": "ofqa9YpQ6iw5tmDsoH5EW1OTMJtKs2Gs",
"AbortOnConnectFail": false,
"IsAdmin": false
}
}Url: Address of your Redis server (can be remote or localhost)
AbsoluteExpirationInHours: The max lifetime for a cache entry
DatabaseId: Redis logical database (usually 0)
Username/Password: For secured Redis clusters
AbortOnConnectFail: Should connections be retried or fail fast
IsAdmin: (Optional) Set to
trueif you want to allow administrative operations likeFlushDb.
⚠️ Security Tip:
Only enable IsAdmin if your use case requires it—such as calling Clear() to flush all keys.
2. Service Registration
After configuring your Redis cache, register REN.Kit for Redis in your Program.cs:
You can now inject IRENCacheService into your classes and use Redis for high-performance, distributed caching.
Here’s how the core registration works under the hood:
3. Why the Multiplexer Factory and Lifetime Are Provided by the Consumer
When registering Redis caching with REN.Kit, the library does not create the ConnectionMultiplexer internally.
Instead, it asks you to provide:
a factory:
Func<IServiceProvider, IConnectionMultiplexer>a lifetime:
RedisMultiplexerLifetime(Singleton / Scoped / Transient)
There are several reasons for this design.
3.1. Full Control Over How Redis Is Configured
Every application has different requirements for how Redis is wired:
Configuration may come from
appsettings.json, environment variables, Vault, Consul, or feature flags.You might need to configure SSL, certificates, custom timeouts, sentinel, or cluster endpoints.
Some applications already have a shared
IConnectionMultiplexerused by other libraries.
By accepting a Func<IServiceProvider, IConnectionMultiplexer>, REN.Kit:
does not assume where or how you load your settings,
lets you use anything already registered in DI (
IConfiguration,ILogger,IOptions<T>, etc.),avoids hard-coding
ConnectionMultiplexer.Connect(...)logic inside the library.
This keeps configuration logic in your application, where it belongs, and keeps the caching library provider-agnostic and clean.
3.2. Correct Lifetime Management (Singleton / Scoped / Transient)
ConnectionMultiplexer is a heavy, expensive object that manages connections, pooling, and reconnections.
StackExchange.Redis recommends treating it as a long-lived, shared object, typically a singleton.
However, not all applications are the same:
A web API or microservice usually wants one singleton multiplexer shared across the entire app.
A multi-tenant system might want:
a scoped multiplexer per tenant or per request in special cases, or
multiple multiplexers for different Redis clusters.
Some advanced / edge scenarios may even want transient multiplexers (e.g., testing, short-lived tools).
By exposing RedisMultiplexerLifetime:
The library does not guess what your lifecycle should be.
You, as the application developer, explicitly choose:
RedisMultiplexerLifetime.SingletonRedisMultiplexerLifetime.ScopedRedisMultiplexerLifetime.Transient
Internally, REN.Kit just translates this into the appropriate DI registration:
This gives you fine-grained control while keeping the API very simple on the library side.
✅ In most real-world applications,
RedisMultiplexerLifetime.Singletonis the recommended choice.
3.3. Testability and Extensibility
Because the multiplexer is provided from the outside:
In unit tests, you can register a fake or mocked
IConnectionMultiplexerwithout touching REN.Kit’s internals.In integration tests, you can swap the real Redis instance with a local container, a different connection string, or a test cluster.
In the future, if you want to:
route to a different Redis cluster,
switch to another implementation that still exposes
IConnectionMultiplexer,
you can do this without changing the library or its public API.
This makes the library easier to maintain, extend, and integrate into complex architectures.
3.4. Clear Separation of Responsibilities
The design follows a simple rule:
Your application is responsible for:
how to connect to Redis,
how long the connection should live,
where configuration comes from.
REN.Kit is responsible for:
how to use Redis once a multiplexer exists,
providing a clean
IRENCacheServiceabstraction,integrating with DI in a consistent way.
By keeping responsibilities separated, the library remains:
framework-agnostic (minimal assumptions),
future-proof (no hard-coded Redis configuration),
and easy to reason about for other developers reading your code.
Why Choose Redis Cache?
Scalable: Multiple app instances can share the same cache instantly.
High Availability: Use with Redis Sentinel or clustering for failover.
Lightning Fast: Network lookups in microseconds, with optional persistence.
Perfect for:
Distributed session storage
User authentication tokens
Large data objects shared across services
Rate limiting, leaderboards, and more
Pro Tips:
Use Redis when your application runs on more than one server, container, or instance.
For cloud or Kubernetes deployments, Redis is almost always the right choice for distributed caching.
Don’t forget: You can override or extend any REN.Kit cache service for custom logic!
Why is Clear() supported for Redis, but not for In-Memory?
Because Redis supports the FLUSHDB operation natively, while IMemoryCache does not support clearing all entries at once.
In distributed environments, this allows you to quickly reset the cache for all connected app instances. Remember to enable "IsAdmin": true if you plan to use this feature.
Last updated