What's Actually Happening
When Redis reaches its configured maxmemory limit, it either evicts keys based on policy or rejects writes with OOM error. If eviction can't free memory or is disabled, you get memory allocation errors.
The Error You'll See
OOM command not allowed when used memory > 'maxmemory'.Or in application logs:
redis.exceptions.ResponseError: OOM command not allowed when used memory > 'maxmemory'.Why This Happens
- 1.maxmemory too low - Limit set too low for workload
- 2.No eviction policy - volatile-lru not configured
- 3.No expiring keys - All keys persistent, nothing to evict
- 4.Large objects - Individual values too large
- 5.Memory fragmentation - Fragmentation wasting memory
Step 1: Check Memory Usage
redis-cli info memoryKey fields:
used_memory:1073741824 # Bytes used
used_memory_human:1.00G # Human readable
used_memory_peak:2147483648 # Peak usage
maxmemory:1073741824 # Configured limit
maxmemory_human:1.00G
maxmemory_policy:noeviction # Eviction policyIf used_memory >= maxmemory, Redis is at limit.
Step 2: Check Current Maxmemory Setting
```bash redis-cli config get maxmemory # 1) "maxmemory" # 2) "1073741824" # 1GB in bytes
redis-cli config get maxmemory-policy # 1) "maxmemory-policy" # 2) "noeviction" ```
Step 3: Increase Maxmemory
```bash # Increase to 2GB redis-cli config set maxmemory 2147483648
# Or set to 0 for no limit (not recommended) redis-cli config set maxmemory 0
# Persist change redis-cli config rewrite ```
Or edit config file:
```bash sudo vim /etc/redis/redis.conf
maxmemory 2gb ```
Step 4: Configure Eviction Policy
Choose appropriate policy:
| Policy | Description |
|---|---|
| noeviction | Return error when memory limit reached |
| allkeys-lru | Remove least recently used keys |
| volatile-lru | Remove LRU among keys with expire set |
| allkeys-random | Remove random keys |
| volatile-random | Remove random keys with expire set |
| volatile-ttl | Remove keys with shortest TTL |
Set policy:
```bash # Recommended: allkeys-lru for cache redis-cli config set maxmemory-policy allkeys-lru
# Persist redis-cli config rewrite ```
Step 5: Check for Keys Without Expiry
# Count keys without TTL
redis-cli --scan | while read key; do
ttl=$(redis-cli ttl "$key")
if [ "$ttl" -eq -1 ]; then
echo "$key"
fi
done | wc -lIf many keys without TTL and using volatile-lru, eviction won't work.
Step 6: Analyze Memory Usage by Key
```bash # Use Redis MEMORY command (Redis 4.0+) redis-cli memory usage mykey
# Sample memory usage of keys redis-cli --sample-keys 1000 memory usage ```
Step 7: Find Large Keys
```bash # Find keys using most memory redis-cli --bigkeys
# Output: # Sampled 1000 keys # Biggest string: 'large-key' (1048576 bytes) # Biggest list: 'my-list' (10000 items) ```
Step 8: Check Memory Fragmentation
redis-cli info memory | grep fragmentationOutput:
mem_fragmentation_ratio:1.50 # 1.5x fragmentationIf ratio > 1.5, significant fragmentation. Restart Redis to defragment, or use active defragmentation:
redis-cli config set activedefrag yesStep 9: Delete Unused Keys
```bash # Delete keys matching pattern (careful!) redis-cli --scan --pattern "cache:*" | xargs redis-cli del
# Set expiry on keys redis-cli expire mykey 3600
# Flush database (nuclear option) redis-cli flushdb ```
Step 10: Upgrade Redis for Better Memory Management
Redis 4.0+ has active defragmentation. Redis 5.0+ has improved algorithms.
redis-cli info server | grep redis_versionVerify the Fix
```bash # Check memory usage redis-cli info memory | grep used_memory_human
# Check eviction is working redis-cli info stats | grep evicted_keys
# Test writes work redis-cli set test "hello" # OK ```
Prevention Tips
```bash # Set appropriate maxmemory (leave room for OS) maxmemory 4gb # On 8GB server
# Use allkeys-lru for cache workloads maxmemory-policy allkeys-lru
# Set TTL on keys SET mykey value EX 3600 # Expire in 1 hour
# Monitor memory usage # Alert when used_memory > 80% of maxmemory ```