Redis maxmemory-policy: Configure Eviction Strategies for Production
Quick Answer
- What it does:
maxmemory-policycontrols how Redis evicts keys when memory usage hits themaxmemorylimit. Chooseallkeys-lrufor most cache workloads,volatile-ttlfor mixed cache/persistent data, ornoevictionto reject writes instead of evicting. - First check: Run
redis-cli INFO statsand inspectused_memory,maxmemory,evicted_keys, andkeyspace_hits/keyspace_missesto understand current memory pressure and hit rates before changing policy. - Minimal fix: Set
maxmemory 256mbandmaxmemory-policy allkeys-lruinredis.conf, or apply at runtime withredis-cli CONFIG SET maxmemory-policy allkeys-lru. - Version boundary: All policies listed here are available in Redis 6.0+. The
allkeys-lrmpolicy (LFU with probabilistic decay) is newer; verify availability withredis-cli CONFIG GET maxmemory-policybefore relying on it. - Critical gotcha: With
volatile-*policies, if no keys have TTL set, Redis behaves likenoevictionand returns OOM errors on writes.
What Problem It Solves
Redis stores data in memory by design. Without a memory cap, a runaway workload can exhaust RAM and crash the process or the host. maxmemory sets the ceiling; maxmemory-policy decides what happens when that ceiling is reached.
The policy answers one question: which keys get evicted when memory is full?
This matters for:
- Cache layers: Hot data should survive eviction; cold data should go first.
- Mixed workloads: You may store both cache data (expiring) and business data (persistent) in the same instance.
volatile-*policies protect non-expiring keys. - Write-heavy systems: If you cannot afford data loss,
noevictionrejects writes with an OOM error instead of silently dropping keys.
Redis offers eight eviction policies, split into two families:
| Family | Policies | Evicts |
|---|---|---|
allkeys-* | allkeys-lru, allkeys-lrm, allkeys-lfu, allkeys-random | Any key, regardless of TTL |
volatile-* | volatile-lru, volatile-lrm, volatile-lfu, volatile-random, volatile-ttl | Only keys with an expiration set |
Plus noeviction, which evicts nothing and returns an error on writes.
When This Error or Setup Appears
You typically encounter maxmemory-policy in three situations:
- OOM errors:
OOM command not allowed when used memory > 'maxmemory'appears when the current policy isnoeviction(the default) and memory is exhausted. Writes fail until memory frees up. - Performance degradation:
evicted_keysclimbs,keyspace_hitsdrops, and cache effectiveness collapses because the wrong keys are being evicted. - Capacity planning: You are deploying a new Redis instance and need to decide how it behaves under memory pressure before it happens.
The configuration is relevant for any Redis deployment—standalone, Sentinel-managed, or Cluster—where memory is finite and eviction behavior matters.
Minimal Working Configuration
Add these lines to redis.conf:
CONFmaxmemory 256mb maxmemory-policy allkeys-lru maxmemory-samples 10
Apply at runtime without restart:
BASHredis-cli CONFIG SET maxmemory 256mb redis-cli CONFIG SET maxmemory-policy allkeys-lru redis-cli CONFIG SET maxmemory-samples 10
Verify:
BASHredis-cli CONFIG GET maxmemory redis-cli CONFIG GET maxmemory-policy redis-cli CONFIG GET maxmemory-samples
To make runtime changes persistent, also run:
BASHredis-cli CONFIG REWRITE
This writes the current configuration back to redis.conf.
Parameters and Environment Variables
Three parameters control eviction behavior:
| Parameter | Default | Description |
|---|---|---|
maxmemory | 0 (no limit on 64-bit) | Maximum memory for cache data. Set to 0 for unlimited. |
maxmemory-policy | noeviction | Eviction strategy when maxmemory is reached. |
maxmemory-samples | 5 | Number of keys sampled for approximate LRU/LFU eviction. Higher values improve accuracy at CPU cost. |
Policy selection guide
| Policy | Best for | Eviction target |
|---|---|---|
noeviction | Data you cannot lose; writes fail when full | Nothing |
allkeys-lru | General cache; hot data concentrated | Least recently used, any key |
allkeys-lrm | Cache with probabilistic decay; newer Redis versions | Least recently used, any key |
allkeys-lfu | Cache with stable hot set; access frequency matters more than recency | Least frequently used, any key |
allkeys-random | Uniform access patterns; no hot/cold distinction | Random key |
volatile-lru | Mixed cache + persistent data; cache keys have TTL | Least recently used, expiring keys only |
volatile-lrm | Mixed workload with probabilistic decay | Least recently used, expiring keys only |
volatile-lfu | Mixed workload with stable hot set | Least frequently used, expiring keys only |
volatile-random | Uniform access among expiring keys | Random expiring key |
volatile-ttl | Shortest remaining TTL first | Key closest to expiration |
Root Cause Analysis
The OOM error OOM command not allowed when used memory > 'maxmemory' has a specific root cause chain:
maxmemoryis set to a finite value.maxmemory-policyisnoeviction(default) or avolatile-*policy with no expiring keys.- Memory usage reaches
maxmemory. - A write command arrives.
- Redis cannot evict anything (noeviction) or finds no eligible keys (volatile-* with no TTL keys).
- Redis rejects the write with an OOM error.
The fix depends on which link in the chain you want to break:
- Raise
maxmemoryif the limit is too low for the workload. - Switch to
allkeys-*if you want Redis to evict any key when full. - Set TTLs on keys if you want to keep
volatile-*policies.
For low hit rates with high evicted_keys, the root cause is usually a mismatch between the policy and the access pattern:
allkeys-lruevicts the least recently used key. If your workload has a stable hot set, this works well.allkeys-lfuevicts the least frequently used key. If access frequency is more stable than recency (e.g., a product catalog where some items are always popular), LFU outperforms LRU.allkeys-randomis almost never the right choice unless access is truly uniform.
Common Errors and Fixes
| Error / Symptom | Root Cause | Fix |
|---|---|---|
OOM command not allowed when used memory > 'maxmemory' | noeviction policy or volatile-* with no TTL keys | Set maxmemory-policy allkeys-lru, or add TTLs to keys, or raise maxmemory |
High evicted_keys, low keyspace_hits | Wrong policy for access pattern | Switch to allkeys-lru for hot-spot workloads, allkeys-lfu for stable frequency patterns |
volatile-* policy but memory still exceeds limit | No keys have TTL set, so policy degrades to noeviction | Set TTLs on cache keys, or switch to allkeys-* |
| Excessive eviction during replication or persistence | maxmemory does not account for replica buffers and persistence overhead | Reserve memory for mem_not_counted_for_evict; consider noeviction for critical data |
| Low eviction accuracy | maxmemory-samples too low | Increase from default 5 to 10 and monitor hit rate |
Production Notes and Security Checks
Memory reservation
maxmemory counts only the data itself, not the memory used by replication buffers, AOF buffers, or client output buffers. If you set maxmemory to 100% of available RAM, Redis may enter an eviction feedback loop where it evicts keys to free memory, but the freed memory is immediately consumed by buffers.
Rule of thumb: Set maxmemory to 70–80% of available RAM on dedicated instances. Monitor INFO memory for mem_not_counted_for_evict to see how much overhead exists.
Cluster considerations
In Redis Cluster, maxmemory is configured per node, not cluster-wide. Each node evicts independently. If data is unevenly distributed, one node may hit its limit while others have headroom.
- Set
maxmemoryper node based on that node's RAM. - Ensure hash slots distribute evenly to avoid one node becoming a bottleneck.
- Monitor per-node
evicted_keysinINFO stats.
Policy safety
- Avoid
allkeys-randomin production unless you have a specific reason. - Avoid
noevictionfor cache workloads—it turns a degraded cache into a failing service. - Use
volatile-*policies only when you consistently set TTLs on cache keys. - Monitor
evicted_keysandkeyspace_hits/keyspace_missescontinuously. A sudden spike inevicted_keysindicates the policy ormaxmemoryneeds adjustment.
Security
Eviction is not a security boundary. If an attacker can trigger eviction, they can cause denial of service by flooding the cache with keys. Protect Redis with:
requirepassfor authentication- Binding to trusted interfaces only (
bind 127.0.0.1or internal IPs) - Disabling
CONFIGcommands in untrusted environments viarename-command
Comparison With Alternatives
| Dimension | Redis | Memcached |
|---|---|---|
| Eviction policies | 9 policies (LRU, LFU, random, TTL, noeviction) | LRU only |
| Runtime policy change | Yes, via CONFIG SET | Requires restart |
| Approximate algorithms | Configurable maxmemory-samples | Fixed |
| TTL-aware eviction | Yes (volatile-* policies) | No |
| Persistence | RDB/AOF available; eviction interacts with persistence | No persistence |
Redis's advantage is flexibility: you can switch policies at runtime without restart, and volatile-* policies let you protect persistent data while evicting cache data. Memcached's single LRU policy is simpler but cannot distinguish between cache and persistent data.
Compared to database-level caching (e.g., MySQL query cache), Redis eviction is more granular and performant, but requires explicit policy management.
FAQ
Q: How do I choose the best eviction policy?
A: Match the policy to your access pattern. If hot data is concentrated (80/20 rule), use allkeys-lru. If access frequency is stable and some keys are always popular, use allkeys-lfu. If access is uniform, allkeys-random may suffice. If you mix cache and persistent data, use volatile-* policies and ensure cache keys have TTLs. Start with allkeys-lru, monitor keyspace_hits and evicted_keys, then adjust.
Q: How does maxmemory-samples affect performance?
A: maxmemory-samples controls how many keys Redis samples before evicting. The default is 5. Higher values produce eviction decisions closer to exact LRU/LFU, but increase CPU usage per eviction. If hit rate is poor, increase to 10 and observe. If CPU is a concern, keep it at 5.
Q: How do I configure maxmemory in Redis Cluster?
A: maxmemory is set per node. Each node's maxmemory should reflect that node's RAM capacity. Eviction runs independently on each node. Ensure data distribution is even across hash slots so no single node hits its limit prematurely. Monitor per-node evicted_keys and used_memory in INFO output.
Q: What happens if I use volatile-lru but no keys have TTL?
A: Redis treats the policy as noeviction. When memory reaches maxmemory, write commands fail with OOM command not allowed when used memory > 'maxmemory'. To fix, either set TTLs on cache keys or switch to an allkeys-* policy.
Q: Can I change the eviction policy without restarting Redis?
A: Yes. Run redis-cli CONFIG SET maxmemory-policy allkeys-lru to change it immediately. Use redis-cli CONFIG REWRITE to persist the change to redis.conf.