Introduction to Redis
What Redis Is and Why It Matters
Redis (Remote Dictionary Server) is an open-source, in-memory data structure store used as a database, cache, message broker, and streaming engine. Because data lives primarily in RAM, Redis delivers sub-millisecond read and write latency — often 100× faster than disk-based databases for hot data workloads.
Redis is not a replacement for PostgreSQL or MySQL. It excels as a complement — holding frequently accessed, ephemeral, or real-time data while the relational database remains the source of truth.
Typical architecture:
Application → Redis (cache / sessions / queues) → PostgreSQL / MySQL (authoritative store)
Core Architecture
Redis is single-threaded for command execution per instance. One thread processes all commands sequentially, which eliminates lock contention and keeps latency predictable. Throughput scales via:
- Pipelining — batch multiple commands in one round trip
- Replication — read scaling from replicas
- Cluster — horizontal sharding across nodes
- Multiple instances — separate Redis for cache vs sessions
Client → TCP connection → Command queue → Single event loop → Response
This design means one slow command (like KEYS * on a large dataset) blocks all other clients on that instance.
Key Features
| Feature | Description |
|---|---|
| In-memory storage | Microsecond latency for reads and writes |
| Rich data types | Strings, hashes, lists, sets, sorted sets, streams, JSON |
| Persistence | RDB snapshots and AOF (append-only file) for durability |
| Replication | Master-replica topology for read scaling and failover |
| Clustering | Horizontal sharding across 16,384 hash slots |
| Pub/Sub | Fire-and-forget messaging between clients |
| TTL (expiration) | Keys auto-delete after a set time — ideal for caches |
| Atomic operations | INCR, SETNX, Lua scripts run atomically |
| ACLs (Redis 6+) | Fine-grained user permissions |
Data Structures at a Glance
# String — counters, simple values, JSON blobs
SET user:1:name "Alice"
GET user:1:name
INCR pageviews
# Hash — object-like field maps
HSET user:1 name "Alice" email "[email protected]"
HGET user:1 email
# List — queues and timelines
LPUSH tasks "send-email"
RPOP tasks
# Set — unique members, tags, relationships
SADD tags:post:42 "redis" "database" "cache"
SMEMBERS tags:post:42
# Sorted set — leaderboards, priority queues
ZADD leaderboard 9500 "player1" 8200 "player2"
ZREVRANGE leaderboard 0 9 WITHSCORES
# Stream — durable event logs
XADD events * action "login" user_id 1001
XREAD COUNT 10 STREAMS events 0
Each structure is optimized for specific access patterns. Choosing the right type avoids awkward JSON serialization and improves memory efficiency.
Common Use Cases
Caching Database Queries
Store expensive query results to avoid repeated disk reads:
import redis
import json
r = redis.Redis(host='localhost', port=6379, decode_responses=True)
def get_user(user_id):
cache_key = f"user:{user_id}"
cached = r.get(cache_key)
if cached:
return json.loads(cached)
user = db.query("SELECT * FROM users WHERE id = %s", user_id)
if user:
r.setex(cache_key, 300, json.dumps(user)) # expire in 5 minutes
return user
A well-designed cache often cuts database load by 80% or more.
Session Store
Web sessions in Redis scale horizontally — any app server reads the same session without sticky load balancing:
SET session:abc123 '{"userId":1,"role":"admin"}' EX 3600
Rate Limiting
# Allow 100 requests per minute per IP (sliding window pattern)
MULTI
INCR rate:192.168.1.1:202406131045
EXPIRE rate:192.168.1.1:202406131045 60
EXEC
Real-Time Leaderboards
Sorted sets maintain ranked scores with O(log N) updates — ideal for gaming and analytics dashboards.
Message Queues
Lists and Streams implement producer-consumer patterns with at-least-once delivery via consumer groups.
Redis vs Alternatives
| Aspect | Redis | Memcached | PostgreSQL |
|---|---|---|---|
| Data model | Rich structures | Strings only | Relational tables |
| Persistence | Optional (RDB/AOF) | No | Yes |
| Query language | Commands | GET/SET | SQL |
| Pub/Sub | Yes | No | LISTEN/NOTIFY |
| Best for | Cache, sessions, real-time | Simple cache | Source of truth |
Use Redis alongside a primary database. Do not store financial transactions or authoritative records solely in Redis without persistence and HA planning.
Quick Start
# macOS
brew install redis
brew services start redis
# Ubuntu/Debian
sudo apt update && sudo apt install redis-server
sudo systemctl enable --now redis-server
# Docker
docker run -d --name redis -p 6379:6379 redis:7-alpine
# Verify
redis-cli ping
# PONG
Basic CLI Session
redis-cli
127.0.0.1:6379> SET greeting "Hello, Redis"
OK
127.0.0.1:6379> GET greeting
"Hello, Redis"
127.0.0.1:6379> INCR pageviews
(integer) 1
127.0.0.1:6379> EXPIRE greeting 60
(integer) 1
127.0.0.1:6379> TTL greeting
(integer) 58
In production, avoid KEYS * on large datasets — use SCAN instead.
Best Practices
- Treat Redis as ephemeral by default unless persistence is explicitly configured
- Set maxmemory and an eviction policy before production traffic
- Use namespaced keys (
app:users:1001) for safe bulk operations - Never expose Redis directly to the internet — bind to private networks, require ACL authentication
- Monitor memory usage, hit rate, and latency with
INFOand tools like RedisInsight or Prometheus exporters
Common Mistakes
| Mistake | Impact |
|---|---|
| Using Redis as primary database without HA | Data loss on crash |
Running KEYS * in production |
Blocks server, latency spikes |
| Storing large blobs (>1 MB) without compression | Memory exhaustion |
| No TTL on cache keys | Stale data and unbounded growth |
| One Redis for everything | Noisy neighbor — split cache vs sessions |
Troubleshooting
Connection refused:
redis-cli ping
# Check: redis-server running? bind address? firewall?
sudo systemctl status redis-server
ss -tlnp | grep 6379
OOM or evictions:
INFO memory
CONFIG GET maxmemory-policy
# Increase maxmemory or fix TTL/eviction policy
Production Scenario
A SaaS API serving 50K requests/minute added Redis as a cache-aside layer in front of PostgreSQL. User profile queries dropped from 12ms p99 to 0.8ms p99. Database CPU fell from 78% to 31%, deferring a planned database scale-up by six months.
What Comes Next
This track covers installation, data structures, caching patterns, pub/sub, sessions, persistence, clustering, Sentinel HA, memory optimization, and production patterns. Redis is one of the highest-impact tools you can add to a web stack — start with caching, then expand into sessions and real-time features as needs grow.