说明:本次草稿依据提交记录,未逐行核对实现。提交未给出迁移脚本的具体 SQL 与细节;查不到的只讲思路,不编造迁移脚本的具体 SQL。

背景:SQLite 到此为止

本项目服务端早期用 SQLite,后来切换到 PostgreSQL。一次提交(2026-10-04)提到存储层切换支持:PG、9 个数据库、48 张表、Redis 任务协调、私有媒体、备份、恢复与墓碑工具;同日还有 退役 SQLite 并保留 PG 恢复能力, 记录清理完成与生产验证, 发布 PG 18 工具与隔离的迁移备份角色, 在严格导入时保留 10 月 2 日遗留肖像 Schema, 快照当前存储实现。

这些提交集中在同一天,说明这是一次有计划的存储层切换。

为什么要换

SQLite 是优秀的嵌入式数据库:单文件、零配置、读写快。对早期单机、单进程的应用完全够用,但应用长大后边界会显现。

首先是多进程与多容器:多个写者同时写同一个 SQLite 文件会很困难,写锁机制不适合高并发写。其次是并发写与租约协调:AI、生成、同步任务需在多进程间协调谁来执行、执行到哪一步、是否重复执行,SQLite 很难提供这种能力;PG 的事务、锁与约束正是为此设计的。最后是运维与恢复:备份、恢复、权限隔离、多角色管理,在 PG 里是成熟能力,在 SQLite 里则需自己拼装。所以 SQLite 不是“不好”,而是“到此为止”。

关键决策:9 个 Schema、48 张表、JSONB

存储文档(2026-10-04 更新)记载:账号、聊天、人物、照片元数据、漫画、AI 计量等在 PG,9 个业务 Schema、48 张原有表,JSON 字段用 JSONB。

9 个业务 Schema 是命名空间划分:把表按业务域分组,既清晰,也便于权限控制;不同业务域的表、权限与演进可相对独立,而不是全堆在一个平面里。

48 张表说明这是整个存储层的搬家,而非几张表的搬家。 提到“清理完成与生产验证”,说明迁完还做了清理与验证,而非迁完就算完。

JSON 字段用 JSONB 是另一个关键决策。很多业务数据是半结构化的,用 JSON 存很方便,但纯文本存 JSON,查询与索引都很弱。JSONB 是 PG 的二进制 JSON 类型:既保留灵活性,又支持索引与查询,适合 AI 计量、聊天记录、人物属性这类半结构化数据。

不可变文件 + PG 指针

存储文档还记载:生活记录正文是账号隔离的不可变 Markdown 文件;记录 HEAD、发布历史、请求回执、租约、同步序列在 PG coordination Schema。

“不可变文件 + PG 指针”是理解这套存储的关键:正文以 Markdown 文件存在,写入后不修改,要改就写新文件;PG 里存指向这些文件的引用:当前 HEAD、发布历史、同步序列。

好处是可追溯、可验证、职责清晰:历史版本不被覆盖,内容写入后不变,文件存正文、库存引用与状态。

写入顺序是:Markdown 对象先完整写入并 fsync,随后 PG 事务发布引用,按账号加事务 advisory lock——先写文件、再发布引用,才能保证数据库指向的文件已存在且完整;advisory lock 保证同一账号的发布串行,不互相覆盖。

旧库导入与 Redis 分工

迁移还有“旧数据怎么搬”。 提到退役 SQLite 并保留 PostgreSQL 恢复能力; 提到在严格导入时保留 10 月 2 日遗留肖像 Schema。“严格导入”即格式不符就拒绝导入,宁可在导入时报错,也不要把脏数据带进新库;但一刀切也会丢掉历史数据。 的做法是严格导入的前提下兼容遗留肖像 Schema:新数据按新 Schema,旧数据按遗留 Schema处理,既不放进脏数据,也不丢历史肖像。

存储文档还记载:接口限流、地图票据、任务和数据通知用 Redis,PG 持久计数、租约、outbox 保持正确性,Redis 失效不放开重复付费请求。这划清了分工:Redis 负责快,PG 负责对;若限流完全依赖 Redis,Redis 一失效,重复付费请求就可能被放进来。关键判断以 PG 为准,Redis 只是加速;Redis 没了,系统可以变慢,但不能变错。

踩坑

第一,存储选型要跟着部署形态走:单机单进程时 SQLite 够用,多进程、多容器、高并发协调时就要换 PG。第二,Schema 划分要按业务域做,让不同业务的表、权限、演进相对独立。第三,JSON 字段要用 JSONB,而非纯文本,半结构化数据既要灵活,也要能查。第四,不可变文件 + PG 指针,写入顺序不能反:先写文件并 fsync,再由 PG 事务发布引用;同一账号用 advisory lock 串行化。第五,旧数据要兼容,但别降低新数据标准:严格导入 + 遗留 Schema 兼容是务实做法。小结:从 SQLite 到 PG,不是简单换库,而是存储职责的重新划分:PG 管持久与正确性,Redis 管速度与协调,文件系统管正文。


2024 | ixs.im
此情此景, [随机]吟诗一首: