All Posts
React

React Server Components Explained (Without the Hype)

March 20, 2025

Server Components get talked about like they're magic. They're not — they solve one specific problem: sending less JavaScript to the browser. Here's what's actually happening under the hood.

SSR vs Server Components

Traditional server-side rendering still ships the full component code to the client so it can "hydrate" — attach event listeners and re-render. Server Components skip that step entirely for components that never need to run in the browser. Their output is HTML plus a serialized description of the tree; the component code itself never crosses the wire.

What You Gain

  • Smaller client JavaScript bundles — server-only components (data fetching, formatting, markdown rendering) add zero bytes to the bundle
  • Direct backend access — a server component can query a database or read a file system directly, no API route needed
  • Automatic code splitting at the server/client boundary

The Rule That Matters

// Server Component — no hooks, no events, can be async
export default async function ProductList() {
  const products = await db.query('SELECT * FROM products');
  return <ul>{products.map(p => <li key={p.id}>{p.name}</li>)}</ul>;
}

// Client Component — needs interactivity
'use client';
export default function AddToCartButton({ id }) {
  const [loading, setLoading] = useState(false);
  return <button onClick={() => setLoading(true)}>Add to cart</button>;
}

Common Misconception

Server Components don't replace client-side state management, they complement it. A server component can render a client component and pass it data as props — the boundary is about where code runs, not about giving up interactivity.