跳到主要内容

SSG 与 SSR:原理、取舍与 SEO 实战

做 SEO 的时候,你经常会听到一句话:“别做纯 CSR,选 SSR 或 SSG。”
但落到项目里,问题通常变成:

  • 页面到底该 静态生成(SSG) 还是 服务端渲染(SSR)
  • 为什么都是“先返回 HTML”,SEO 和性能表现却差很多?
  • 动态数据、个性化、频繁更新、海量页面……怎么兼顾?

这篇文档会把 SSG 与 SSR 的核心机制讲清楚,并给出面向 SEO 的选型与落地清单。

结论先行(最快能用的结论)
  • 内容稳定 + 页面量大 + 希望极致性能与最低成本:优先 SSG(必要时再加 ISR/增量更新)。
  • 内容强动态 + 个性化 + 需要实时数据/权限判断:优先 SSR(并配合 CDN/服务端缓存)。
  • 最常见的真实情况是混合:公开内容页用 SSG/ISR,登录后页面用 SSR/CSR。

一、先把名词说清:你到底在“渲染”什么?

无论 SSG 还是 SSR,本质都在解决同一件事:让爬虫/用户尽快拿到“包含主要内容的 HTML”,而不是只拿到一个空壳。

页面渲染通常分两段:

  1. 首屏 HTML(可被抓取):标题、正文、列表等“主要内容”要出现在初始 HTML 中
  2. Hydration(水合,可交互):浏览器下载 JS,把静态 HTML 变成“能点击/能跳转/能提交”的应用
常见误解

“SSG/SSR = 不需要 JS 了” 是误解。
多数现代框架(React/Vue)仍然需要在浏览器侧 Hydration 才能完成交互,只是 关键内容不再依赖浏览器执行 JS 才出现

二、SSG 是怎么工作的(构建时生成)

SSG(Static Site Generation)把“生成 HTML”的时机放到构建阶段:提前把每个页面的 HTML 产物生成好,然后部署到 CDN。

2.1 SSG 的 SEO 与性能特点

  • SEO 友好:初始 HTML 里就有标题、正文、结构化数据,爬虫抓取成本低
  • 性能强:静态文件 + CDN,通常有更好的 TTFB 与稳定性
  • 成本低:不需要为每次请求做服务端渲染,服务器压力小

2.2 SSG 的核心代价

  1. 数据新鲜度:构建之后内容变了,页面不会自动更新
  2. 构建耗时:页面越多,构建越慢(尤其是“万级页面”)
常见解法:SSG + 增量更新(ISR 等)

很多框架提供“增量静态生成/再验证”的能力:让页面先用静态方式响应,再在后台更新并逐步生效,从而兼顾性能与更新频率。

三、SSR 是怎么工作的(请求时生成)

SSR(Server Side Rendering)把“生成 HTML”的时机放到每次请求到来时:服务器拿到请求,拉取数据,生成 HTML,返回给用户/爬虫。

3.1 SSR 的 SEO 与业务优势

  • 内容实时:每次请求都能拿到最新数据(新闻、库存、价格、权限)
  • 更适合个性化:可根据 Cookie/登录态/地理位置渲染不同内容
  • 状态码更自然:404/301/302 等可在服务端直接控制(对 SEO 很关键)

3.2 SSR 的核心代价

  • 服务器开销更大:每次请求都要计算渲染
  • 可用性更敏感:渲染链路依赖 API/数据库,任何抖动都可能影响出 HTML
  • 缓存策略更复杂:既想“实时”,又想“快”,就需要分层缓存(CDN/应用缓存/数据缓存)

四、SSG vs SSR:用 SEO 视角做一次对比

维度SSGSSR
HTML 生成时机构建时请求时
首屏内容可抓取性很强(天然)很强(天然)
内容更新频率低~中(可配增量更新)高(天然实时)
TTFB(首字节)通常更低(CDN 静态)取决于渲染耗时与缓存
服务器成本中~高
“海量页面”能力构建会变慢(需拆分/增量)请求会变多(需缓存/扩容)
典型场景文档、博客、营销页、帮助中心新闻、商品详情(强动态)、搜索结果页、个性化首页
SEO 里最容易踩的坑

不管你是 SSG 还是 SSR,只要出现以下情况,SEO 都会显著变差:

  • 关键内容在浏览器 useEffect 之后才出现(爬虫可能抓不到)
  • <title> / description / canonical 等元信息只在客户端修改
  • 统一返回 200,但页面里写着“未找到”(应该返回 404

五、如何选型:一张决策图

六、实战:以 Next.js 为例理解落地方式

下面用 Next.js(Pages Router)快速演示 SSG 与 SSR 的写法,重点是理解“数据在什么时候拿、HTML 在什么时候生成”。

为什么用 Next.js 举例?

它把 SSG/SSR 的差异表达得很直观(getStaticProps vs getServerSideProps),便于迁移到 Nuxt、Remix 等框架的对应能力。

6.1 SSG:构建时生成页面

// pages/posts/[id].tsx
export async function getStaticPaths() {
const ids = await fetch('https://api.example.com/posts/ids').then((r) => r.json());
return { paths: ids.map((id: string) => ({ params: { id } })), fallback: false };
}

export async function getStaticProps({ params }: { params: { id: string } }) {
const post = await fetch(`https://api.example.com/posts/${params.id}`).then((r) => r.json());
return { props: { post } };
}

要点:

  • getStaticProps构建时拉取数据并生成 HTML
  • getStaticPaths:告诉框架要生成哪些动态路由页面

如果内容需要“准实时”,可以加入再验证(ISR):

return { props: { post }, revalidate: 60 };

含义:页面最多每 60 秒更新一次(具体行为取决于部署平台实现)。

6.2 SSR:请求时生成页面

// pages/profile.tsx
export async function getServerSideProps({ req }: { req: { headers: Record<string, string> } }) {
const cookie = req.headers.cookie ?? '';
const user = await fetch('https://api.example.com/me', { headers: { cookie } }).then((r) => r.json());
return { props: { user } };
}

要点:

  • getServerSideProps每次请求都会执行
  • 非常适合登录态、权限、强个性化内容(但记得做缓存与降级)
SEO 实战提醒

如果这是公开可索引的页面(比如商品详情),SSR 里要确保:

  • 返回的 HTML 包含完整标题/正文/结构化数据
  • 缺货/下架要么做明确的状态码策略(404/410/301),要么做可理解的替代页

七、SSG/SSR 的 SEO 清单(上线前自检)

  • 初始 HTML 是否包含主要内容(不要依赖客户端二次渲染)
  • title/description/canonical 是否在服务端就确定(不要只在客户端改)
  • 分页/筛选页是否有 canonical 与 noindex 策略(避免重复内容)
  • 404/重定向是否返回正确状态码(不是“200 + 文案提示”)
  • 是否输出 sitemap.xml / robots.txt(便于收录与抓取预算管理)
  • 结构化数据是否可被抓取(JSON-LD 推荐,且放在初始 HTML)

更多通用 SEO 细节可以配合阅读:SEO 搜索引擎优化完全指南

八、常见坑与排查思路

  1. “看起来是 SSR/SSG,但爬虫抓到的是空页面”
    • view-source: 或抓包看“返回的 HTML”是否有正文
    • 不要只看 Elements(Elements 可能是 Hydration 后的 DOM)
  2. Hydration mismatch(服务端 HTML 与客户端渲染不一致)
    • 避免在首屏渲染中使用 Date.now() / Math.random() 等不稳定值
    • 把“只在浏览器才知道的信息”(窗口尺寸、localStorage)延后处理
  3. SSG 构建时间爆炸
    • 拆分构建:按目录/语言/站点拆分
    • 引入增量生成/按需生成,避免一次性生成全量页面
  4. SSR 性能波动大
    • CDN/应用层缓存 + 数据层缓存分层做
    • 给慢接口设置超时与降级(宁可展示旧数据,也别长时间白屏)

九、面试高频问答

Q1:SSG 和 SSR 最大区别是什么?
A:区别是 HTML 生成时机:SSG 在构建时生成静态 HTML;SSR 在每次请求时由服务器渲染生成 HTML。

Q2:为什么 SSR/SSG 更利于 SEO?
A:因为爬虫请求页面时就能拿到包含主要内容的 HTML,不需要依赖执行 JS 才能看到正文与元信息。

Q3:SSR 一定比 SSG 慢吗?
A:不一定。SSR 如果命中 CDN/服务端缓存也可以很快;但在“无缓存 + 渲染依赖多接口”的情况下,SSR 更容易慢且波动大。

Q4:SSG 的内容更新怎么解决?
A:常见做法是增量更新(ISR/再验证)、触发式重建(Webhook)、或对局部数据使用客户端请求(但要避免影响 SEO 关键内容)。

Q5:Hydration 是什么?为什么会出现 hydration mismatch?
A:Hydration 是浏览器把“服务端/静态 HTML”变成可交互应用的过程。Mismatch 往往来自“服务端渲染结果”和“客户端首次渲染结果”不一致,例如时间戳、随机数、依赖浏览器环境的逻辑。

Q6:为什么说“不要用 200 返回 404 页面”?
A:搜索引擎会把它当作正常页面收录,造成索引污染与重复内容;正确做法是返回 404(或 410)状态码。

Q7:哪些页面更适合 SSG?
A:文档、博客、营销页、帮助中心、公司介绍、长期稳定的落地页等。

Q8:哪些页面更适合 SSR?
A:强动态/强个性化页面,例如:登录态首页、订单中心、搜索结果页、库存价格实时变化的页面等。

Q9:如何在 SSR 场景提升性能?
A:关键是缓存:CDN 缓存(按路由/参数)、应用缓存(渲染结果缓存)、数据缓存(接口/数据库结果缓存),并结合超时与降级策略。

Q10:SSG/SSR 与 Core Web Vitals 有什么关系?
A:SSG/SSR 能提升首屏可见速度(FCP/LCP)并减少“白屏时间”。但最终指标还受资源体积、图片、布局稳定性、交互脚本等影响,渲染方式只是其中一环。