目录
首页 » 博客 » 脚本详解:generate-archive.ps1 [切换主题] [English]

脚本详解:generate-archive.ps1

归档 · 标签云 · 最新文章 · 搜索索引


这个脚本干什么

generate-archive.ps1 是整个构建流程的第一站。它扫描所有博客内容文件,提取元数据,一口气生成四种东西——最新文章组件、文章归档页、标签云页、以及搜索索引。四种产出分别服务于侧边栏、独立页面、和 CGI 搜索引擎。

它必须在 build.ps1 之前跑,因为 build.ps1 需要读取它生成的 latest-posts.html 注入侧边栏。如果顺序反了,访问者看到的就是旧数据。这个依赖关系由 rebuild-all.ps1 保证,不需要人工记忆。

元数据扫描

脚本的第一件事是遍历博客目录,从每个 .html 文件的 HTML 注释中提取四段元数据:

  • 日期date)—— 兼容 2026-04-282026-04-28 23:30 两种格式
  • 标题title)—— 文章的显示名称
  • 标签tags)—— 逗号分隔的关键词,用于标签云
  • 草稿标记draft: true)—— 如果存在,整篇文章被跳过,不出现在任何产出中
  • 所有文章信息存入一个 PowerShell 对象数组,按日期降序排列。这一步是整个脚本的数据基础,后续四种产出都从这个数组派生。

    产出 A:最新文章组件

    取前 5 篇文章,生成 src/components/latest-posts.html。这个文件会被 build.ps1 注入到每个页面的右侧边栏,所以网站上的"最新文章"列表永远是最新的。

    这里有一个值得说的细节:标题截断用的是像素宽度估算而非字符数。中文字符估算 11px,ASCII 估算 6px,总宽度超过 110px 就截断到 10 个字符。用字符数截断对于纯中文没问题,但中英混排的标题会差很多——"AAAAAAAAAA" 和 "中中中中中"同样是 5 个字,像素宽度能差一倍。在 CSS text-overflow 出现之前,手工宽度计算是唯一的方案,而且恰好 IE5.5 不支持 text-overflow

    输出文件用 UTF-8 without BOM 编码。因为它会被注入到已有 BOM 的页面中, 带 BOM 的话注入位置会多出乱码字符。

    产出 B:文章归档页

    归档页的核心是按年-月分组。日期格式统一为 YYYY-MM-DD, 取前 7 个字符就是 YYYY-MM。用 PowerShell 的 Group-Object 一键分组,然后按月份降序排列,最新的排最上面。

    每个月份渲染为一个标题("2026年4月")+ 一个两列表格:左边是日期(黄色,130px 宽),右边是文章标题(青色链接)。这个页面没有侧边栏——它采用双栏布局,左边放博客文章,右边放其他页面(下载中心、FAQ 等),用 980px 的 table 居中。

    归档页输出到 dist/archive.html(中文)或 dist/en/archive.html(英文)。

    产出 C:标签云页

    标签云是四个产出中逻辑最复杂的一个。它需要构建一个标签→文章的反向索引:遍历所有文章的标签,用一个哈希表把每个标签映射到包含它的文章列表。

    标签的字号根据文章数量分级:3 篇以上大号(size="4"),2 篇中号(size="3"), 1 篇小号(size="2")。三个级别足够区分,不需要更复杂的热度算法。

    标签云下方是每个标签对应的文章列表,用 <a name="tag名"> 做锚点,点击标签云中的链接即可跳转。标签云也有独立的中英文版本。

    产出 D:搜索索引

    搜索索引是一个纯文本文件 data/build/search_index.txt, 被 cgi-bin/search.py 读取用于全文搜索。格式是每篇文章一个 TITLE/DATE/LINK/TEXT 记录块,用 --- 分隔。

    文本提取的流程很简单:读 HTML → 正则剥离所有标签 → 替换   → 压缩连续空白为单个空格。不需要 NLP,不需要分词,纯字符串匹配。对于几十篇文章的个人博客,这个方案完全够用。

    搜索是完全免 JavaScript 的——搜索框是一个 HTML 表单,提交到 CGI, 服务端做全文匹配,返回带高亮的结果页面。整个过程和 2002 年的搜索引擎工作原理一致。

    双语支持

    脚本通过 -Lang 参数控制语言(默认 "zh")。英文模式下,博客内容从 blog/en/ 读取,界面文字自动切换("最新文章"→"Latest Posts"), 输出到 dist/en/ 子目录。中文和英文的归档、标签、搜索索引完全独立, 不会混在一起。

    设计思路

    如果把这个脚本拆成四个独立的脚本,代码会更模块化,但每次全站构建需要扫描 4 次博客目录。 一次扫描、四处输出的设计减少了 I/O。在这个只有几十篇文章的站点上,差异可能只有几百毫秒,但它体现了一种"提前想好数据流"的工程习惯——知道数据从哪里来、要到哪里去、中间经过几次变换。

    PowerShell 的 Group-ObjectSort-ObjectSelect-Object 等管道命令在这里发挥了类似 SQL 中 GROUP BYORDER BYLIMIT 的作用—— 只不过操作的是内存中的对象数组而非数据库表。



    昵称
    内容

    « 留言板架构记录 « 返回主页 脚本详解:generate-rss.ps1 »
    工具
    [工具箱]

    最新文章

    » 西数HC620食用指南
    » 脚本概览
    » 2026年5月 · ...
    » IE 5.5 兼容性审查
    » 当前站点架构更新分析...

    » 文章归档

    本文标签

    教程 网站建设 脚本

    DRAGONRSTER
    CC BY-NC-SA
    © 2004-2026 DragonRSTER • Made with HTML • 本站支持IE5.5+
    资源许可 • 最佳浏览分辨率:1024x768 • 本页最后更新于 2026年05月05日 23:15:10