一万篇 Markdown 之后:静态博客的性能拐点与应对
一万篇 Markdown 之后:静态博客的性能拐点与应对
October 7, 2026
静态博客在几百篇时几乎不会遇到性能问题。但跨过某个量级后,四个原本不存在的麻烦会同时出现。
拐点一:构建耗时
这是最先暴露的问题。不同生成器在 1 万页量级的差距是数量级的:
| 生成器 | 1 万页全量构建 | 运行时依赖 |
|---|---|---|
| Hugo | 10–30 秒 | 无(Go 单二进制) |
| Zola | 30–60 秒 | 无(Rust 单二进制) |
| Astro | 3–8 分钟 | Node |
| VitePress / Hexo | 10 分钟起 | Node |
| Jekyll | 十几分钟起 | Ruby |
如果每天发布多次并走 CI,分钟级构建的累积成本会非常可观。这也是我们在 blog.35plus.tech 选择 Hugo 的直接原因。
拐点二:搜索索引
大多数博客主题内置 Fuse.js,实现方式是把全站内容的 JSON 推给浏览器。几百篇时这个 JSON 只有几百 KB,1 万篇时会膨胀到 20MB 以上——首屏直接被拖死。
正确做法是 Pagefind:索引在构建期生成并分片,用户搜索时浏览器只拉取命中的那几片。
hugo --minify --gc # 先构建
npx pagefind --site public # 再建索引Pagefind 官方数据:1 万页站点的完整搜索请求总传输量在 300KB 以内,多数站点约 100KB。它还原生支持中文分词,这一点对中文博客是刚需。
拐点三:列表页与归档
如果首页渲染"全部文章",1 万篇会生成一个巨大的 HTML。必须做两件事:
- 首页只取最近 20 篇,配合
featured推荐位 - 归档页按 年 → 月 两级聚合,绝不做全量列表
标签页同理,每页 20 条分页。另外标签总数建议控制在 300 以内,否则要合并同义词,不然标签云本身就失去了导航价值。
拐点四:sitemap 与 feed
- sitemap 由 Hugo 自动分片成
sitemap.xml+ 子索引,无需手工处理 - RSS 只输出最近 50 条,否则 feed 文件体积会失控,订阅客户端也会卡
目录分片同样重要
单目录文件数超过 3000 后,文件系统遍历、git 操作、编辑器索引都会明显变慢。所以内容目录要按年月分:
content/posts/2026/10/xxx.md
content/posts/2026/11/xxx.md这个结构还有一个附带好处:date 元信息落到了路径上,即使 front-matter 缺失也能推断。
结论
万级规模下,静态站依然是最省心的方案——但前提是把这四个拐点提前处理掉,而不是等它炸了再补。