Files
blog/.spec/specs/archive/2026-10-24_migrate-blog-content/spec.md
T
wait4xandGLM-5.3 aea21c8694 feat(migrate): Halo 全量内容迁移(压缩版)——6文/21图/1瞬间 URL 1:1
- 正文源=线上渲染页(Halo 快照层 patch 残迹:泥潭/赎罪仅 2 字符),
  pandoc html→gfm + tags API 显示名换算后分类:5 书评(五档情绪色)+1 技术
- 图库 21 张:长边 2400/q86 压缩入仓(原图 196M→9.5M——公开仓历史膨胀
  与 nginx 100M 推送上限双杀;原图在 Phase 0 备份 tar 中永久留档)
- 瞬间 1 条;URL 1:1(6 slug 全等,零 301)
- 本提交由 7 个本地提交重写而成(清除已进历史的 196M blob,未推送过);
  因 reset --soft 暂存竞态,一并包含 spec 归档文件
  (.spec/specs/archive/2026-10-24_migrate-blog-content/)

验证: check_urls.py 6==6;astro build 11 页 exit 0(8.67s);
      EXIF 管线跑通;staging 更新;halo healthy+200 全程未动

Co-authored-by: GLM-5.3
2026-10-25 00:39:08 +08:00

77 lines
3.9 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# Phase 2:Halo 内容迁移(6文/21图/1瞬间,URL 1:1)- 项目范围
<!-- spec-format: 2 -->
## 1. 问题定义
- **项目目标**:把 Halo 生产内容(6 篇文章 + 21 张图库照片 + 1 条瞬间)迁入 Astro 集合,URL 与旧站 1:1,生产 Halo 全程只读不动
- **目标用户**:站长(迁移完成后新站具备真实全量内容,具备上线条件)
- **核心价值**:内容资产零丢失转移;SEO 无损(同 slug)
## 2. 假设与待确认
### 2.1 已确认事实
- Halo 公共 API 可匿名读:posts 列表含 status.content(HTML);photos 插件 /apis/api.photo.halo.run;moments /apis/api.moment.halo.run
- 现有 slugs:deng-dai-ge-duo/hai-feng-zhong-shi-luo-de-xie-se-kui-zeng/mian-sha/shu-zui/ni-tan/cs-ge-lei-pei-zhi(首查实测,其中技术文旧 slug 为 csge-lei-pei-zhi 需在迁移时核对)
- pandoc 可用(~/.local/bin)
- Phase 1 集合 schema:posts(category/tags/mood)/photos(json sidecar+jpg)/moments
### 2.2 关键假设
- Halo 正文内嵌图片走 /upload/ 相对路径,可经 127.0.0.1:18090 直下
- 引文(blockquote)经 pandoc 转 md 后结构保留,无需人工重排
### 2.3 待确认问题
- [x] 文章内嵌图与图库照片是否同一批(书评封面 vs 独立照片)→ 结论:正文零内嵌图,封面图独立未迁(原站亦独立),已记 spot-check 人工项
### 2.4 可选解释与取舍
- pandoc + python 后处理 > 纯手写解析器:覆盖面与可维护性 -> 选 pandoc
- 迁移中间产物(导出 JSON/原始 HTML)不入库(.migration/ gitignore),脚本与最终内容入库
### 2.5 已证伪路径
- 无
## 3. 功能范围
### 3.1 核心功能(MVP)
- [x] T1 Halo 全量导出脚本(posts/photos/moments/附件,中间产物 .migration/)
- [x] T2 文章 HTML→MD 转换 + frontmatter 组装 + 图片本地化
- [x] T3 图库 21 张迁移(下载+sidecar+EXIF+分组)
- [x] T4 瞬间迁移
- [x] T5 URL 1:1 断言脚本(旧 slug 集 == 新 slug 集)
- [x] T6 全站构建 + staging 更新 + 抽检清单
### 3.2 扩展功能
- 无
### 3.3 不在范围内
- 双语翻译(Phase 3)、上线切换(Phase 4)、Halo 停用(Phase 5)、旧站评论(数为 0)
## 4. 最小实现路径
- 最简单可行方案:导出/转换/断言脚本入 scripts/migrate/,一次性中间产物 .migration/(gitignore);真实内容直接覆盖同 slug 样例文件
- 暂不引入:评论迁移(存量为 0)、双语分流(Phase 3)、封面图 frontmatter 扩展
- 不做的抽象/配置化:不写通用 CMS 迁移框架,只服务本次 Halo 一次性迁移
## 5. 技术决策
- 技术栈:python3 + pandoc + curl
- 证据协议:evidence: runs
- 本轮允许改动:scripts/migrate/、content/、.gitignore、.spec/、src/(仅消费侧微调如分组枚举)
- 本轮不应触碰:~/docker_apps/halo 运行实例与 postgres、nginx、其它 infra
- Git integration branch:`spec/2026-10-24_migrate-blog-content`
### 5.1 验证策略
- 范围级别:package
- 变更对象:content/ 三集合、scripts/migrate/ 脚本、.gitignore
- 快速检查:`pnpm astro build`
- 集成检查:URL 1:1 断言 + 全量路由产物存在(6 文章页)
- 全项目检查:staging 更新 + rollback-dryrun 仍绿;仅在内容 schema 或构建链变更时升级范围重跑
- 升级触发:只有改动集合 schema、构建链或部署脚本时,才升级验证范围并记录理由
## 6. 成功标准与验证方式
- [x] 6 篇文章新站路由全存在且 slug 与旧站一致 -> verify: task_0005
- [x] 图库 21 张全量呈现(EXIF 提取成功数记录) -> verify: task_0003
- [x] 瞬间 1 条迁移 -> verify: task_0004
- [x] 生产 Halo 状态未变(healthy + 200) -> verify: task_0006
## 7. 风险与约束
- Halo HTML 含编辑器私有结构(嵌入块)→ pandoc 后人工抽检点写入 T6 清单 -> 抽检覆盖
- 附件 URL 形态不一(相对/绝对)→ 下载器双形态兼容