前端进阶之旅前端进阶之旅
  • 基础篇HTML/CSS/JS 打底
  • 进阶篇原理与工程化
  • 高频篇面试最常问的那批
  • 精选篇按模块收敛的总结
  • 手写篇常考代码手写实现
  • 面经篇真实面试问题复盘
  • AI 篇NEWAI 时代的前端考点
  • 历年面经NEW按年份追踪真实考点
  • 每日一题每天一道,攒手感
  • 专项自测100 题快速查漏
  • 小程序题库小程序专项刷题
  • 算法题库NEW在线编码即时判题
  • 知识卡片NEW碎片时间过考点
  • 面试题大全常见问题解析
  • AI 答疑NEW随时提问,即时解析
  • AI 模拟面试NEW模拟真实面试 + 报告
  • AI 定制路线NEW按你的简历现排
  • AI 知识地图NEW串起全站知识点
  • 原理篇React / Vue 源码拆解
  • HTTP从报文一路讲到 HTTPS
  • 浏览器渲染、事件循环、进程
  • 计算机基础Linux、网络、操作系统
  • 设计模式23 种模式怎么用
  • Node学习指南从环境搭建到服务端
  • NPM工作流script、依赖与发布
  • Docker容器化部署上手
  • Canvas图形与动画实战
  • 前端系统进阶学习大型项目工程化
  • 前端综合文章长期沉淀的实践文
  • 思维导图知识点全景图
  • 学习路线按图索骥不跑偏
  • AI 热点NEWAI 每日动态
  • 公众号动态公众号历史文章
  • 博客动态站长的技术博客
  • 开发者导航常用工具与文档站
  • 基础篇HTML/CSS/JS 打底
  • 进阶篇原理与工程化
  • 高频篇面试最常问的那批
  • 精选篇按模块收敛的总结
  • 手写篇常考代码手写实现
  • 面经篇真实面试问题复盘
  • AI 篇NEWAI 时代的前端考点
  • 历年面经NEW按年份追踪真实考点
  • 每日一题每天一道,攒手感
  • 专项自测100 题快速查漏
  • 小程序题库小程序专项刷题
  • 算法题库NEW在线编码即时判题
  • 知识卡片NEW碎片时间过考点
  • 面试题大全常见问题解析
  • AI 答疑NEW随时提问,即时解析
  • AI 模拟面试NEW模拟真实面试 + 报告
  • AI 定制路线NEW按你的简历现排
  • AI 知识地图NEW串起全站知识点
  • 原理篇React / Vue 源码拆解
  • HTTP从报文一路讲到 HTTPS
  • 浏览器渲染、事件循环、进程
  • 计算机基础Linux、网络、操作系统
  • 设计模式23 种模式怎么用
  • Node学习指南从环境搭建到服务端
  • NPM工作流script、依赖与发布
  • Docker容器化部署上手
  • Canvas图形与动画实战
  • 前端系统进阶学习大型项目工程化
  • 前端综合文章长期沉淀的实践文
  • 思维导图知识点全景图
  • 学习路线按图索骥不跑偏
  • AI 热点NEWAI 每日动态
  • 公众号动态公众号历史文章
  • 博客动态站长的技术博客
  • 开发者导航常用工具与文档站
首页程序员面试题库Next.js 服务端读取 数据库 API
NeNext.js数据与缓存

在 Next.js App Router 中,服务端如何读取数据库或 API 数据?与客户端读取有何本质区别?

在 Next.js App Router 中,服务端组件直接读取数据库或 API,客户端则需通过接口。差异在执行位置和渲染时机,并决定是否支持 SSR/SSG。

前端进阶之旅 · 一题精讲更新于 2026.09.05
Next.js#数据与缓存#路由#异步编程#缓存
先看核心答案
理解线索

服务端 vs 客户端读取

  1. 服务端渲染期在请求或构建时执行数据库查询
  2. 浏览器运行时通过 API 获取数据并处理状态
  3. hooks 禁用服务端组件不能有事件和状态

如果数据仅用于加快首屏并无需交互,必须走服务端读取。

核心回答

先记住这个答案

在服务端组件中,您可以定义异步组件并直接 await 数据库查询或 fetch,因为代码运行在服务器上,凭证不会发送到浏览器。客户端组件无法访问数据库,通常通过调用自己的 API 路由或使用 SWR/React Query 获取数据。核心区别是:服务端读取发生在请求时(或构建时),可与缓存配合实现 SSG/SSR 数据预加载;客户端读取发生在浏览器中,交互性更强但凭证有风险且无法供搜索引擎预取。因此,可公开且用于首屏的数据应优先在服务端获取。

  • 服务端组件可异步访问数据库或外部 API
  • 客户端必须通过 API 或数据请求库获取数据
  • 服务端读取是 SSR/SSG 数据预加载的前提

服务端读取为何发生在渲染阶段

在 App Router 中,服务端组件是异步函数。将页面或组件标记为 async 后,您可以直接 await fetch() 或使用 ORM 访问数据库。由于渲染工作在服务器上执行,数据库密码、API 密钥等凭证不会打包进客户端 JS。每个请求都会重新执行渲染(除非启用静态生成),因此数据获取与渲染合为一体,发生在构建时或每次请求期间。

与客户端组件不同,服务端组件不使用 useState、useEffect 等 hook。这些 hook 依赖于浏览器交互和生命周期。如果企图在服务端组件中使用它们,React 会报错,导致页面无法预渲染。因此,凡是需要 SSR/SSG 的首屏数据,必须在服务端获取;交互后的再请求则由客户端另行发起。

展示产品列表的工程取舍

假设要搭建 /products 页面,需从 PostgreSQL 读取产品表,并联合第三方价格 API。产品数据公开且变化不频繁,希望搜索引擎能索引全部内容。选择服务端组件:页面 async function Page() 内同时启动数据库查询和外部 fetch,使用 Promise.all 并行等待;数据库连接直接使用服务端凭证,外部 API 密钥放在 NEXT_PUBLIC_ 以外的环境变量中。

如果改用客户端组件,则必须先创建 API 路由 /api/products 来包装这两个数据源,浏览器加载性能、SEO 和响应速度都会受影响。服务端方案在首屏时,HTML 已含完整数据,并且可以利用 Next.js 的缓存和 revalidate 机制,实现按需增量更新。因此对公开数据、需要预渲染的产品页,服务端读取是更直接、安全的做法。

何时必须放弃纯服务端读取

服务端读取适合用于不依赖浏览器状态的页面:如博客、公开目录。若页面必须读取登录用户的私有数据,且要展示实时头像或个性化设置,则不能把用户 ID 写在客户端请求里,必须让服务端通过身份统一从 session 取得。这种情况仍用服务端读取,但数据结果不能静态缓存,需设为按请求刷新。

另一种边界是数据更新极快且需 WebSocket 推送,例如聊天室或股票行情。服务端每次请求只能拿到瞬间状态,配合 revalidate: 0 会频繁重渲染,风险高。正确做法是外层用服务端提供骨架和首屏,实时部分用独立的客户端组件订阅推送。判断依据:这些数据是否必须在 HTML 里提前出现;若不需要就不该占用服务端渲染,否则会阻塞整条路由。

回答前,多想一步

容易答错的地方

误认为服务端组件可以用 `useEffect` 发起请求
服务端组件没有生命周期,不能使用 useEffect、useState。它们是异步函数,数据只在渲染开始时获取。若在服务端组件中引入这些 hook,构建时就会类型错误或运行时报错。正确的服务端读取就是直接 await 数据,若需交互则改用客户端组件。
误认为 `fetch` 默认缓存所以服务端数据都能被 CDN 缓存
自 Next.js 15 起,fetch 在服务端组件中默认不缓存,每次请求都会重新执行。若需要缓存,必须显式使用 next: { revalidate } 或设置 use cache 指令。只有静态生成(SSG)时数据才会在构建时快照。因此,希望通过服务端读取提升性能,必须主动控制缓存策略。
试着用自己的话回答

面试官还会怎么问?

服务端读取一定会阻塞页面渲染吗?

如果没有用流式渲染,服务端组件中的 await 会阻塞该路由的渲染,直到所有数据返回。要避免阻塞,可将不重要的数据放到 <Suspense> 边界内,让其他部分先发送给浏览器。官方建议对每个慢数据请求单独用 <Suspense>,配合 loading.js 提供骨架屏。

客户端组件能访问服务端环境变量吗?

不能。服务端环境变量(如 DB 密码)只存在于服务端进程。客户端组件若通过 fetch 调用自己的 API 路由,则由该路由的服务端代码读取环境变量,最终只把响应数据发给浏览器。使用仅客户端变量如 NEXT_PUBLIC_* 才会被公开打包,切勿放入密钥。

若同一份数据在多个服务端组件中用到,会重复请求吗?

每次请求的同一个渲染期内,Next.js 会自动对相同 URL 的 fetch 做 memoization,但仅限一次请求内。如果涉及数据库,推荐用 React 的 cache() 包裹查询函数,确保同一请求的多次调用共享同一 Promise,从而避免重复查询。该缓存不跨请求共享,每次请求都有独立范围。

从一道题,走向一组知识

把知识连起来

数据与缓存

在一个 Next.js 页面中,如果需要从多个不同的 API 源获取数据,如何合理设计数据获取流程以避免性能瓶颈?

同属「数据与缓存」专题,接着看 Next.js 多源数据 获取协调 在具体场景中的处理方式。

数据与缓存

在 Vercel 等部署平台中,Next.js 的缓存策略在构建时与运行时有何不同?哪些数据会进入边缘缓存?

同属「数据与缓存」专题,接着看 Next.js 部署 缓存策略 边缘缓存 在具体场景中的处理方式。

参考资料

  • Fetching Data

示例用于理解所注明的运行环境与边界;延伸学习可结合原文中的更多案例。

本题目录
  1. 先记住这个答案
  2. 服务端读取为何发生在渲染阶段
  3. 展示产品列表的工程取舍
  4. 何时必须放弃纯服务端读取
  5. 容易答错的地方
  6. 面试官还会怎么问
  7. 把知识连起来
读懂,再试着讲出来

先看核心答案,再读代码。最后展开追问,检查自己有没有遗漏边界。

试着回答追问
浏览全部面试题理解原理,也关注真实的使用场景。回到顶部 ↑