Glossary

Cache

A cache is a fast, temporary storage layer that stores results of expensive operations (database queries, API calls, computations) so subsequent requests for the same data can be served faster without repeating the expensive work.

Explanation

Caching is the fundamental performance optimization: avoid repeating expensive work by storing the result and reusing it. This principle appears at every level: CPU caches, OS page cache, browser caches, and application-level caches (Redis, Memcached). Cache patterns: Cache-Aside (lazy loading) — on a cache miss, fetch from the database, store in cache, return; on subsequent requests, return from cache. This is the most common pattern. Write-Through — write to cache and database simultaneously (no stale data, but slower writes). Write-Behind — write to cache, asynchronously persist to database (fast writes, but data may be lost if cache fails before persisting). Eviction policies determine what to remove when cache is full: LRU (Least Recently Used) — removes the item accessed least recently; good general-purpose. LFU (Least Frequently Used) — removes the item accessed least often; better for skewed access patterns. TTL (Time-To-Live) — removes items after a fixed duration; simple, predictable staleness. "There are only two hard things in Computer Science: cache invalidation and naming things." When underlying data changes, cached copies must be updated or removed. Strategies: TTL expiry (accept staleness up to N seconds), event-driven invalidation (on write, delete the cache entry), versioned keys (embed version in key, increment on update).

Code Example

javascript
// Redis cache-aside pattern (Node.js)
const redis = require('redis');
const client = redis.createClient({ url: process.env.REDIS_URL });
await client.connect();

async function withCache(key, ttlSeconds, fetchFn) {
  const cached = await client.get(key);
  if (cached) return JSON.parse(cached); // cache hit

  const data = await fetchFn();          // cache miss: fetch from source
  await client.setEx(key, ttlSeconds, JSON.stringify(data));
  return data;
}

// Cache expensive DB query for 5 minutes
app.get('/api/products', async (req, res) => {
  const products = await withCache(
    'products:all',
    300,
    () => db.query('SELECT * FROM products WHERE active = true')
  );
  res.json(products);
});

// Invalidate on write
app.put('/api/products/:id', async (req, res) => {
  await db.query('UPDATE products SET ...', [req.body, req.params.id]);
  await client.del('products:all'); // invalidate cached list
  res.json({ ok: true });
});

Why It Matters for Engineers

Caching is one of the highest-impact performance improvements in backend development. A query that takes 100ms from PostgreSQL takes 1ms from Redis — a 100x speedup. For high-traffic endpoints, this translates to dramatically reduced database load, lower infrastructure costs, and better user experience. Caching is also essential systems design knowledge. 'Design a URL shortener,' 'design Twitter,' and 'design a leaderboard' all involve caching decisions. Knowing cache strategies, eviction policies, and invalidation patterns is expected at senior engineer interviews.

Learn This In Practice

Go deeper with the full module on Beyond Vibe Code.

Systems Design Fundamentals → →