Is Next.js Frontend or Backend? Understanding the Full-Stack Architecture

Next.js is both frontend and backend—it is a full-stack React framework that ships a Node.js server runtime alongside a client-side browser bundle.

If you are wondering whether Next.js is frontend or backend, the answer depends on which part of the codebase you examine. The framework controls both sides of the request lifecycle, allowing you to write Server Components that execute during the HTTP request and Client Components that hydrate in the browser.

What Makes Next.js Full-Stack?

Next.js is not a pure client-side library like Create React App, nor is it a standalone backend framework like Express. Instead, it bundles two distinct runtimes:

  • Server runtime: Located in packages/next/src/server/, the core NextNodeServer class implements the HTTP API, API routes, middleware, edge functions, and the React Server Components (RSC) rendering pipeline.
  • Client runtime: Located in packages/next/src/client/, a thin bootstrap registers the global window.next object, hydrates the page, and provides the client-side router and web-vitals utilities.

Because the framework owns both the request handling and the browser hydration, a single Next.js app can render Server Components, serve API endpoints, and execute client-side navigation—all from the same codebase.

How Next.js Bridges Frontend and Backend

The architecture relies on several key subsystems that pass data between the server and browser.

The Server Core

In packages/next/src/server/next-server.ts, the NextNodeServer class orchestrates incoming requests. It determines whether to:

  • Serve a static file from the build output
  • Execute an API route handler
  • Run middleware at the edge
  • Stream a React Server Component payload

This server can run on Node.js or Edge runtimes (Web API), making it capable of backend logic regardless of the hosting environment.

The Rendering Pipeline

When a page request arrives, the server enters the rendering pipeline defined in files like packages/next/src/server/render.tsx and lazyRenderAppPage.ts. This pipeline:

  1. Executes Server Components to fetch data and generate HTML
  2. Streams the RSC payload to the client
  3. Injects the client bootstrap script

The Client Bootstrap

Once the browser receives the HTML, packages/next/src/client/next.ts initializes. It:

  • Hydrates the React tree using the streamed payload
  • Instantiates the client-side router (packages/next/src/client/router.ts)
  • Enables prefetching and fast navigation without full page reloads

Where Is the Frontend/Backend Boundary?

Next.js does not enforce a hard network boundary. Instead, it uses file conventions and directives to decide where code executes.

Server Components (Backend Execution)

Any component in the app/ directory that does not contain the 'use client' directive is a Server Component. It executes exclusively on the server during the request, can access Node.js APIs, and never ships JavaScript to the browser.

Client Components (Frontend Execution)

Adding 'use client' to the top of a file tells Next.js to bundle this component for the browser. It hydrates on the client, can use useState, useEffect, and browser APIs, but cannot access server-only resources during render.

API Routes (Dedicated Backend)

Files in pages/api/ or app/api/ define backend endpoints. These execute only on the server, receive NextApiRequest and NextApiResponse objects (or Web standard Request/Response in the App Router), and return JSON or streams.

Middleware (Edge Backend)

The middleware.ts file runs before a request reaches a page. It executes on the Edge runtime (or Node.js in recent versions), allowing you to rewrite, redirect, or authenticate at the network edge.

Practical Examples of Next.js Frontend and Backend Code

Combining Server and Client Components

This example demonstrates how Next.js mixes frontend and backend execution in a single page:

// app/page.tsx (Server Component - Backend)
import LikeButton from './ui/like-button'

export default async function Page() {
  const post = await fetch('https://api.example.com/post/1').then(r => r.json())
  
  return (
    <main>
      <h1>{post.title}</h1>
      <p>{post.body}</p>
      <LikeButton initial={post.likes} />
    </main>
  )
}
// app/ui/like-button.tsx (Client Component - Frontend)
'use client'

import { useState } from 'react'

export default function LikeButton({ initial }: { initial: number }) {
  const [likes, setLikes] = useState(initial)
  return <button onClick={() => setLikes(l => l + 1)}>👍 {likes}</button>
}

The page fetches data on the server (backend), while the button handles state in the browser (frontend).

Creating a Backend API Endpoint

// pages/api/hello.ts
import type { NextApiRequest, NextApiResponse } from 'next'

export default function handler(req: NextApiRequest, res: NextApiResponse) {
  res.status(200).json({ message: 'Hello from the server!' })
}

Accessing /api/hello executes this function on the Node.js server, proving Next.js can function as a backend framework.

Implementing a Custom Server

// server.js
import { createServer } from 'http'
import next from 'next'

const dev = process.env.NODE_ENV !== 'production'
const app = next({ dev })
const handle = app.getRequestHandler()

app.prepare().then(() => {
  createServer((req, res) => {
    // Custom backend logic can be inserted here
    handle(req, res)
  }).listen(3000, () => console.log('> Ready on http://localhost:3000'))
})

This demonstrates that Next.js provides the NextNodeServer class that powers both the default and custom backend implementations.

Key Source Files That Define Next.js Architecture

Understanding whether Next.js is frontend or backend requires examining these critical files in the repository:

Summary

  • Next.js is both frontend and backend, functioning as a full-stack React framework that controls the entire request lifecycle.
  • The server runtime (NextNodeServer in packages/next/src/server/) handles HTTP requests, API routes, middleware, and Server Component rendering.
  • The client runtime (packages/next/src/client/) hydrates server-generated HTML and provides SPA navigation through the client-side router.
  • The boundary between frontend and backend is determined by the 'use client' directive—files without it execute on the server, while files with it ship to the browser.
  • API routes and Middleware provide dedicated backend endpoints and edge-level request processing, confirming Next.js's server-side capabilities.

Frequently Asked Questions

Is Next.js primarily a frontend framework?

No, Next.js is not merely a frontend framework. While it builds upon React for UI rendering, it ships with a complete Node.js server (NextNodeServer) that handles HTTP requests, executes API routes, and renders Server Components. According to the source code in packages/next/src/server/next-server.ts, the framework orchestrates both the request handling (backend) and the client hydration (frontend), making it a full-stack solution.

Can Next.js be used for backend-only applications?

Technically yes, though it is uncommon. You can create a Next.js application that contains only API routes (pages/api or app/api) and no pages, effectively using it as a backend server. The packages/next/src/server/route-modules/pages-api/module.ts file implements this functionality, allowing you to handle HTTP requests and return JSON without serving any HTML. However, Next.js is optimized for applications that combine both frontend and backend concerns.

How does Next.js decide whether code runs on the frontend or backend?

Next.js uses file conventions and directives to determine execution context. In the App Router, any component without the 'use client' directive is treated as a Server Component and executes exclusively on the server during the request. Files that include 'use client' at the top are bundled for the client and hydrated in the browser. For API routes and middleware, the framework always executes these on the server (Node.js or Edge runtime) as defined in packages/next/src/server/next-server.ts.

What is the difference between Next.js API routes and Server Components?

API routes are explicit backend endpoints that execute when a specific URL path is requested (e.g., /api/data). They receive raw HTTP requests and return JSON or other data formats, implemented in packages/next/src/server/route-modules/pages-api/module.ts. Server Components, conversely, are React components that render during the page request to generate HTML, but they are not exposed as standalone HTTP endpoints. They can fetch data and render UI, but they return React elements rather than raw API responses, and they are part of the rendering pipeline in packages/next/src/server/render.tsx.

Have a question about this repo?

These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:

Share the following with your agent to get started:
curl -s "https://instagit.com/install.md"

Works with
Claude Codex Cursor VS Code OpenClaw Any MCP Client

Maintain an open-source project? Get it listed too →