系列文章 · 00–10

MUSE / ARCHITECTURE NOTES

Muse 智能体 · 状态层详解

本篇目录
  1. 0. 一句话状态层
  2. 1. DB 平面总览:196 表 / 18 schema 的验证(11-04;10-17 为 194/17)
  3. 2. 逐 schema 导览(18 个,11-04 快照;10-17 为 17 个)
  4. 3. DB 与文件:分工判定规则
  5. 4. `muse.db` 只读通道:Agent 侧唯一 DB 入口
  6. 5. 文件平面:目录地图实况
  7. 6. 双轨实体的分工解剖
  8. 7. 投影 ≠ 本体:全系统反复出现的模式
  9. 8. 恢复与检查点:VM 可替换的底气
  10. 9. 边界:状态层在本机看不见的部分
  11. 附录 A. 逐 schema 表数表(实测:解析 schema.md 求和验证;明细为 10-17 快照)
  12. 附录 B. 本机状态快照(实测,2026-10-17 深夜)

配套《00-Muse技术架构解构》的 §8 展开篇。调查日期:2026-10-17(Asia/Shanghai)。 证据范围:/opt/muse/skills/muse_db/ 技能包全套参考(SKILL.md + references/schema.md + references/querying.md + references/identifiers.md + references/tables/ 逐表指南)、muse.db 工具当场实测查询、本机 home 与 ~/workspace/ 目录实况清点、~/docs/ 与 system prompt 的状态相关明文。 标注规则同主报告:实测 = 本机命令/工具当场验证;文档 = 本地 docs/system 文件明文;推断 = 由表结构/文件形态拼出、未经服务端证实。 复核修订:2026-11-04(Asia/Shanghai)——基于当前会话运行时逐项重测;DB 表数/schema 数与文件侧数字凡未注日期者均为 11-04 快照,10-17 旧数见各处双日期标注;muse.db 行数快照(§4.3/附录 B)与附录 A 各 schema 明细为 10-17 口径(文内已注明,未重测)。


0. 一句话状态层

Muse 的状态不在 Agent 进程里,而在三个平面上:Postgres 状态库(结构化本体:196 张表 / 18 个 schema(11-04 快照;10-17 为 194 表 / 17 schema,新增 saved),事件账本 + 检查点 + outbox)、文件系统(语义层:Markdown 记忆、目标工作区、会话转录 JSONL、人可读的投影)、运行时易失状态(套接字、锁、就绪标记、变更信号文件)。DB 与文件之间靠水位线/指纹/epoch 做带新鲜度建模、可失效、可重算的投影同步("最终一致"的收敛保证未验证,见 §7);靠恢复所有权 + 代次 + 检查点实现 VM 被整体替换后的接管恢复(恢复语义是检查点+投影重建,不是事件重放,见 §1.1/§8)——这正是 00 §8 那句「运行时即数据库」的完整展开。

┌─ DB 平面(本体) Postgres 196 表 / 18 schema(11-04;10-17 为 194/17)
│    runtime.events 事件账本 · agent.context_items 有序上下文
│    检查点/恢复所有权 · 各域 outbox · 水位线与投影表
├─ 文件平面(语义层 + 投影)
│    ~/MEMORY.md + ~/memory/(记忆叙事) · ~/agents/<id>/sessions/*.jsonl(转录)
│    ~/workspace/goals/(目标工作区) · ~/workspace/cron.d/(调度投影,只读)
│    ~/workspace/space_data/spaces.catalog.*(产物目录信号)
├─ 同步/信号平面
│    ~/.postgres-ready · ~/runtime.lock · ~/.hatch-db-change-signals/
│    DB 行的 source_watermark / fingerprint / stale_after / writer_epoch
└─ 读通道(Agent 侧唯一入口)
     muse.db 受限只读 SELECT(安全屏障视图) + 专用产品工具(写路径)

1. DB 平面总览:196 表 / 18 schema 的验证(11-04;10-17 为 194/17)

实测验证方法(不靠 00 的转述,当场重数;11-04 复核用同方法重测):

  1. 解析 references/schema.md 的全部条目链接:去重后恰 196 个 schema.table,按 ### <schema> 分节计数求和 = 196,分节数 = 18(新增 saved:saved.items / saved.item_links 2 表;10-17 为 194/17,逐项明细见附录 A);
  2. references/tables/ 目录下逐表指南文件数同为 196 个,一表一文件(11-04 复测;10-17 为 194);
  3. schema.md 页首标注其生成来源:迁移集 5af4f2bfdee2b934a53bbcc22602c602ab85059e0ac97ea20137fd299c06036b(文档)——即这份目录是某次迁移快照的产物,线上实际表数可能随部署漂移,引用时应以「该迁移集口径」理解;
  4. muse.db 活查询抽验多表 count(*) 均可达且返回合理量级(见 §4.3),证明目录与活库对应、非纸面清单。

1.1 从表结构读出的设计风格(实测列定义,风格归纳为推断)

风格 证据(表/列) 含义(推断)
事件账本打头 runtime.events(有序事件账本,带请求归因);agent.runtime_state.last_event_seq 外键指回它;runtime.tool_calls/tool_outputs 各有 event_seq 唯一键 一切先落成有序事件,再投影成各域当前态;event_seq 是审计追溯与恢复定位的坐标("读到哪了"),不是 event sourcing 式的重放起点——恢复走检查点+投影(见 §8),因为事件载荷是不透明 text 且大量状态(文件、外部世界)本就不在事件里,从事件流重放出完整状态在结构上不可能。
软引用多于硬外键 大量列标注 “Soft local reference”;memory.claims.supersedes_claim_id / run_id 明示 “Opaque correlation identifier; no declared local table relationship”;identifiers.md 须按域上下文消歧同名 ID 跨域解耦:各 schema 可独立演进/清理,完整性靠应用层而非 DB 约束
JSON 装进 text 列 payload_json / state_json / item_json / execution_config_json 普遍为 text 而非 jsonb(少数如 memory.claims.evidence_handles、feed.run_steps.output_json 用 jsonb) 载荷当不透明字节存取,结构演进不触发迁移;查询面只暴露扁平化投影(runtime.event_payload_fields、agent.context_item_fields)
时间戳双制 agent.* 多用 timestamp with time zone + now();scheduler.* 多用 bigint epoch(*_utc / *_at_ms) 两个子系统世代不同:调度器按 epoch 毫秒做跨时区算术,Agent 域用 timestamptz 做审计呈现(推断)
单例表 runtime.writer_epoch(singleton bool PK)、scheduler.scheduled_resume_state(singleton bool PK) 全局唯一状态行当「寄存器」用:写者 epoch、下一次唤醒投影
outbox 反复出现 scheduler.delivery_outbox、feed.fleet_engagement_outbox / fleet_reaction_outbox、agent.message_mailbox、agent.context_item_derived_write_backlog、runtime.chat_event_derived_write_backlog 「先落表、再投递、可重试」是全系统的投递语义基线(见 §7、§8)

2. 逐 schema 导览(18 个,11-04 快照;10-17 为 17 个)

完整计数见附录 A;下表只讲「这个 schema 在状态层里扮演什么角色」,代表表均取自 schema.md 的一句话定义(文档)。11-04 仅复核总数(196)与 schema 数(18,新增 saved),各 schema 明细表数为 10-17 快照(未重测)。

schema(表数) 角色 代表表 → 存什么
runtime(38) 运行时总账:事件、消息、工具、工单、检查点 events 有序运行时事件账本(请求归因);messages 消息角色/文本/事件引用;tool_calls+tool_outputs 工具调用与结果全记录;work_items 持久化工单(父/请求/会话关系);browser_tasks 浏览器任务所有权与执行态;context_snapshots 带来源水位线的版本化上下文快照;writer_epoch 可靠卷当前写者 epoch
agent(25) Agent 本体:身份、会话、上下文、恢复 agents 身份/种类/会话/父关系;agent_ancestors 祖先链与距离;context_items 有序可读会话条目(消息/工具引用);compactions+agent_compactions 压缩检查点与摘要;runtime_restart_checkpoints 重启恢复检查点;recovery_owners 可恢复工作的持久所有权与代次;message_mailbox 已受理提交的排序与路由态;subagent_spawns/progress 子 Agent 派生与进度;token_usage 用量归因
ideas(22) Ideas 卡片与策略学习管线 ideas 卡片本体(描述/理由/类别);idea_quality 相关性/新颖度/可行性评分;idea_dedup 指纹与去重映射;bandit_arm_state / bandit_fold_state / bandit_folded_events 策略学习统计、折叠水位线、已折叠事件;feed_snapshots(+cards/sections) 快照三件套
feed(16) Feed 生成、发布与 fleet 同步 units 生成内容与版次/来源 prompt;runs+run_steps 生成运行与步骤尝试;prompts 保存的 brief 与启用态;fleet_publish_state 已发布贡献的水位线;fleet_engagement_outbox / fleet_reaction_outbox 待发布互动/反应(带重试态);preferences_projection 由互动折叠出的当前偏好投影
self_improvement(13) 后台进化流水线的账本(02 篇 Part II 的状态面) runs 改进运行(objective/阶段);objective_state+objective_markers 目标当前态、源修订与进度标记;leases 改进工作的租约与所有权;handoff_dedupe 已发 handoff 的防重记录;connector_read_audit 连接器读取的目的与请求归因(审计);calculation_records / calibration_records 计算与校准的证据句柄
device(13) 配对设备的同步副本 nodes 配对设备、广播命令与已启用权限;contacts(+contact_emails/phones/addresses 三张标签子表) 同步联系人;calendar_events 同步日历;call_log 通话记录;data_sync_state 每设备的同步游标与全量同步范围;upload_sessions / upload_chunks / media_upload_batches / media_upload_events 上传会话、分片摘要与处理车道
scheduler(12) 定时任务的定义、运行与投递 jobs 保存的计划/启用态/来源;job_definitions 版本化定义与 prompt 引用;job_runs 每次运行(定义版本/起止);cron_mutations 变更审计(请求归因);delivery_outbox 待投递结果(见 §7);scheduled_resume_registrations/state 唤醒注册与下一次唤醒投影;doctor_* 维护任务的计划与证据
goals(12) 目标域本体(与 ~/workspace/goals/ 文件工作区双轨,见 §6) goals 目标描述与生命周期态;updates 带日期的进展更新;actions+thread_actions 行动项及其与对话线程的链接;briefings 简报位置与打开时间;momentum_history 进展评估与调整建议;learning_state 学习类目标的先修/掌握证据/误解;suggestions 目标↔想法链接
activity(8) 活动监控面(App 里「正在做什么」的呈现层) activity_monitor_threads 线程身份/呈现/当前态;…_thread_sections / …_thread_actions 分节与动作(含 Agent 归因);…_agent_threads / …_message_threads / …_runtime_work_threads / …_carrier_user_messages 四张链接表把 Agent、消息、持久化工单挂到同一线程;feed_entries 工作/消息/目标的活动条目
health(8) 健康数据的同步与聚合 samples+sample_values 原始测量与命名值/单位;aggregates 按时段+时区聚合;sleep_sessions、workouts 专题表;events+record_values 事件与记录值;synced_ranges 每来源/类别已同步的时间范围(游标,见 §8)
memory(6) 记忆的机器层(与 Markdown 记忆双轨,见 §6.1) claims 记忆主张:引文、出处(source_path/source_line)、重要度、置信度、supersedes_claim_id 替代链、首见/强化/有效期;entries 索引条目:memory_uri、分块、来源位置(citation_path/line_start/line_end)、隐私分类;embeddings+embedding_models 检索向量与模型/维度/距离度量;entry_attributes 条目命名属性;metadata 子系统元数据
media(4) 媒体库索引 items 媒体清单(来源身份/类型/文件位置);descriptions 生成描述及模型/版本;exif_values 抽取的 EXIF;locations 坐标与地理编码状态
chat(3) 聊天规范层(side chat 的本体在此,不在文件,见 §5.3) chats 规范聊天元数据(chat_id = 根会话 UUID);message_bindings 供应商消息 ↔ 原生会话 ↔ Muse 消息的绑定;event_transports 聊天事件的供应商归因
podcasts(3) 播客产物登记 episodes 剧集(描述/音频路径/时长);feeds feed 身份与发布 URL;feed 旧版单 feed 配置(遗留表与新表并存,演进痕迹)
spaces(9) Artifact(空间)的登记与调用 spaces 产物清单(名称/源码位置/会话关联);proposals 提案与确认态;shares 分享设置与发布态;action_invocations / action_arguments / action_results 产物 action 的请求—参数—结果三段;file_artifact_identities 文件产物的稳定身份;user_state 收藏/访问史/排序
ingest(1) 外部数据源入口 data_source_events 数据源事件(有序、带来源)——单表 schema,最薄的入口层
shell(1) 客户端外壳偏好 user_state 外壳条目的收藏/访问史/排序——与 spaces.user_state 同构(推断:各表面一份 user_state 是通用小模式)
saved(2,11-04 新增) — saved.items / saved.item_links——10-17 快照无此 schema,用途未细查(❓)

分布形态(实测计数,10-17 明细;占比按 11-04 总数 196 重算):头部三家 runtime+agent+ideas = 85 表(43.4%)——状态层的重心是「运行时自身」而非用户内容;用户内容域(goals/feed/device/health/media/chat/podcasts)合计 57 表(29.1%);横切域(scheduler/self_improvement/activity/memory/spaces/ingest/shell)52 表(26.5%);11-04 新增 saved(2 表,1.0%)。


3. DB 与文件:分工判定规则

从双轨实例反推的判定规则(推断,实例均为实测):

进 DB 的 进文件的
需要有序/事务/跨实体关联的(事件 seq、所有权、代次、outbox 重试态) 人要读、要改、要引用的叙事(MEMORY.md、GOAL.md、技能/连接器文档)
高频小粒度写入(context_items 逐条、tool_outputs 逐次) 低频整篇修订(每日 memory 日志、对齐合成)
机器消费的索引/向量/评分(memory.entries/embeddings、ideas.idea_quality) 交付物本体(报告、表格、artifact 源码、媒体文件;DB 只登记路径/身份)
权限与生命周期状态(device.nodes 的启用权限、goals 的生命周期态、spaces.shares 的发布态) 工作区草稿与中间产物(goals/*/agent_notes、feed/research/)

一句话:DB 存「系统必须算对的」,文件存「人必须看懂的」;同一实体常两边都有,DB 侧是登记/状态/索引,文件侧是内容/叙事/工作区。


4. muse.db 只读通道:Agent 侧唯一 DB 入口

4.1 约束清单(文档:SKILL.md + querying.md + 工具定义)

  • 单条、受限、只读:一次提交一条 bounded SELECT;底层是最小权限 DB 角色,仅对目录内允许关系有 SELECT,不能改数据;
  • 词表封闭:只能用 querying.md 列出的内置函数(约 120 个)与转型拼写;非递归 CTE 名必须以 hatch_cte_ 开头,递归 CTE 直接拒;集合聚合(json_agg/jsonb_agg/array_agg/string_agg)被禁(防在输出限额前先构造无界值);联表时投影列必须别名唯一(重复输出名拒);
  • 域外即不可见:Postgres 系统目录、迁移簿记、备份表、凭据、Sentinel 审批库、每个 artifact 的 app.db 都在此面之外;凭据(令牌/密码/密钥/支付秘密)永远在凭据服务之后,此面只可见非秘密的生命周期记录(如 spend-request 状态);
  • 受保护内容走安全屏障视图:私有模型推理(thinking/redacted-thinking)永不可读;逐轮保存的 developer 指令同样 withheld;受影响的表经 security-barrier view 读取,withheld 列会以「未知列」报错、被过滤的行无声缺席——查不到 ≠ 不存在,须先读逐表指南的 read restrictions 再下结论;
  • 定位纪律:普通产品读写优先用专用工具(chat/goal/artifact/feed/scheduler/connector…),它们持有产品语义且可能含 DB 之外的活状态;muse.db 只用于诊断缺失/孤儿记录、重建执行史、查跨域不一致(SKILL.md 明文)。

4.2 限额(本会话工具返回实测)

工具每次返回自带 limits,本会话两次查询一致:

限额 值
max_rows 200 行
max_output_bytes 262,144 字节(256KiB,即 00 §8 所说「262KB 输出上限」的精确值)
max_row_bytes 65,536 字节/行
query_timeout_ms 5,000(即 00 所说 5s 的精确口径:工具层总超时)
statement_timeout_ms 3,000(语句层超时,比总超时更紧)

4.3 活库抽验快照(实测,2026-10-17 深夜本会话)

count(*) 一批(同一工具、同一分钟内):

表 行数 对照
agent.agents 163 与 ~/agents/ 目录数 163 精确吻合(§5.2)
agent.context_items 2,413 上下文条目总账(含全部 Agent)
runtime.messages / runtime.events 588 / 593 消息数与事件数同量级,事件略多(推断:含非消息事件)
runtime.tool_calls 0 计数面与明细面口径差或该表走屏障视图过滤(见下注)
scheduler.jobs / scheduler.job_runs 28 / 532 定义 28、运行史 532(约 19 次/定义)
goals.goals 3 与 ~/workspace/goals/ 三个目标目录吻合
chat.chats 5 本机聊天总数(主 + side chats)
memory.claims / memory.entries 4 / 98 主张层薄、索引层厚(见 §6.1)
ideas.ideas / feed.units / spaces.spaces 94 / 63 / 2 内容域量级
self_improvement.runs 190 进化流水线累计运行(02 篇的账本实证)
device.nodes 1 已配对设备 1 台
agent.runtime_restart_checkpoints 1(count) 但明细 SELECT 返回 0 行——见下注
agent.recovery_owners / agent.compactions / runtime.workflow_runs / agent.sessions / media.items 0 当前无恢复所有权登记、无压缩记录、无 workflow 运行、会话表为空(会话实体在文件侧,§5.2)

注(实测现象,解释为推断):runtime_restart_checkpoints 的 count(*) 得 1、明细查询得 0 行;runtime.tool_calls 计数为 0 而本会话显然发生过大量工具调用。二者都符合 querying.md 的警告——受屏障视图/行过滤影响的表面上,不可见 ≠ 不存在,计数与明细的口径也可能不同。这是本报告对「只读通道」最重要的一条使用纪律,压过任何单次查询结果。

4.4 写路径不变量:Agent 是状态层的纯读者

本篇所有证据拼出一条架构定理:Agent 侧对 DB 只有 muse.db 这一条只读通道(§4.1–§4.3);一切写 DB 的动作都由 daemon/服务端进程执行,Agent 的"写"(建 cron、记目标、存记忆、发消息)本质是调专用产品工具,由工具经可信侧落库。

这是 06 篇 privsep 隔离在状态面的镜像:执行面是"Agent 不碰凭据",状态面是"Agent 不碰 DB 写"。两层合起来,Agent 进程的破坏半径被收敛到"调工具"+"写自己的 workspace 文件"。该不变量的反例搜索(Agent 直连 Postgres 的 socket/DSN)本轮未做,列为待验证 ❓。


5. 文件平面:目录地图实况

5.1 home 根:注入文件与运行时标记(实测)

路径 实测 性质
~/MEMORY.md 22,389 B(11-04;10-17 为 5,284 B) 长期记忆精选层,每轮注入(00 §9)
~/AGENTS.md / SOUL.md / IDENTITY.md / USER.md / TOOLS.md 886 / 795 / 254 / 335 / 337 B 注入文件组(操作手册/人格/身份/用户档案/工具笔记)
~/HEARTBEAT.md / PROACTIVE_PREFERENCES.md 113 / 496 B 心跳清单与主动消息偏好(00 §11)
~/runtime.lock 0 B 运行时单实例锁(存在即标记,内容为空)
~/.postgres-ready 6 B,内容 ready DB 就绪门(推断:启动序里 DB 就绪后才拉起依赖它的组件)
~/.hatch-db-change-signals/ 8 个 spaces.catalog.* 信号文件(11-04;10-17 为 4 个,各 61–62 B) DB 变更→文件侧的失效信号(与 ~/workspace/space_data/ 下同名 catalog 文件成对出现;推断:文件观察者靠它刷新产物目录缓存)

5.2 记忆与会话:两个「agents」目录必须分清(实测)

记忆树 ~/memory/(共 37 个文件、1.8M;10-17 为 18 个文件、144K):

  • 根:按日日志 28 篇(2026-09-26.md … 2026-11-04.md,合计 812,581 字节;10-17 为 10 篇 / 41,653 B)——当日活动量直接写在文件大小上;
  • bank/ 4 篇:world.md 32,729 B、reflections.md 28,290 B、experience.md 970 B、opinions.md 68 B——运行时托管的长期沉淀(00 §9 的「bank」层),体量远大于每日日志,是真正的厚资产;
  • people/ 3 人页 + INDEX.md(11-04;10-17 为 2 人页,页数随用户变化);groups/ 仍仅 INDEX.md(尚无群组页,11-04 复核);
  • ~/memory/index/ 本机不存在:00 §9 转述的通用结构里有 index 层,本机实况只有 bank 一个托管子目录——索引功能实测由 DB 的 memory.entries/embeddings 承担(§6.1),文件侧 index 目录或是其他形态/已演进(推断)。

会话转录 ~/agents/(home 根,非 workspace):1,417 个 agent-<uuid>/ 目录(11-04;10-17 为 163 个)。每目录固定 sessions/<uuid>.jsonl + sessions/sessions.json 各一份(10-17 为 163+163 实测)——每个 Agent 一份 append-only 转录。这是 DB agent.agents 163 行的文件侧孪生(10-17 实测数量吻合;11-04 文件侧为 1,417 目录,DB 行数未复测,该吻合论断以 10-17 为准):DB 管身份/关系/状态,JSONL 管逐字转录(推断分工)。

工具输出溢出 ~/workspace/agents/:278 个 <uuid>/ 目录(11-04;10-17 为 90 个,00 晚间口径 89),每目录仅 tool-output/ 一项,且绝大多数为空:10-17 实测全树仅 2 个实际输出文件(11-04 未复测)。说明该目录是按需落盘的溢出区(工具输出超限/需留存时才写文件并回传句柄),不是全量日志——全量在 DB runtime.tool_outputs 与转录 JSONL 里。

5.3 workspace 侧主要状态目录(实测)

路径 实况 本体在哪
~/workspace/goals/(6.6M,10-17) 12 个目标目录(11-04;10-17 为 3 个),每目标同构 7 件(10-17 实测):GOAL.md / files/ / hidden_files/ / briefs/ / crons/ / agent_notes/ / references/ 内容与工作区在文件;生命周期/行动/动量在 DB goals.*(§6)
~/workspace/cron.d/ 10 个子目录(minutely/hourly/daily/weekly/monthly/yearly/runonce/secondly + _archive/_invalid),现行投影 2 个(minutely/heartbeat__interval@30m.md + runonce/ 1 个),_archive/ 4 篇(11-04;10-17 为现行 1 个 + 归档 1 篇) 投影:本体在 DB scheduler.jobs(28 条,10-17 快照)+ job_definitions;文件名即计划编码(名__周期@时刻.md);prompt 明文禁止直改投影,须走 cron 工具改本体。28 条定义只投影出个位数文件——推断:投影只含用户面可见的 job,系统/目标内嵌 job 不落此目录
~/workspace/system/system_prompt.md 73,296 B 单文件(11-04;10-17 为 71,868 B) 主聊天启动时落盘的 prompt 快照,本身就是「DB/运行时→文件」的一次投影(00 §3)
~/side-chats/ 本机不存在 side chat 本体在 DB(chat.chats 5 行 + runtime.messages);文档里的 ~/side-chats/<id>/MEMORY.md 路径模式在本机未物化为目录——该形态或是按需生成/其他表面专用(推断)。这是「DB 原生、文件缺席」的实例,与 cron 的「DB 本体+文件投影」恰成对照
~/dreams/ 根 17 篇日期反思(11-04;10-17 为 4 篇)+ alignment/derived/ 4 文件 + alignment/repair/ 2 文件(后两项 10-17 实测) Dreaming 流水线产物(02 篇 Part II);其中 derived 的对齐合成每轮注入上下文
~/workspace/self_improvement/ objectives/(8 个 objective,11-04;10-17 为 7 个,各带 CURRENT.md + archive/ 历史版)+ staging/(各次运行的暂存区)+ migrations/relationships/ 进化层的文件账本:DB self_improvement.* 管运行/租约/去重,文件管每 objective 的当前态全文与归档链
~/workspace/feed/ research/(按 feed-id 分目录的调研素材)、media/(1p/3p/staging/ + index.json)、runs/(空) 素材在文件;单元/运行/发布水位线在 DB feed.*
~/workspace/space_data/ spaces.catalog.<ts>.<n> 信号文件多份 与 §5.1 的变更信号呼应;~/workspace/spaces/ 本身为空目录,~/workspace/ts-spaces/ 下 2 个空间(ai / space)与 DB spaces.spaces 2 行吻合
~/workspace/proactivity/hidden_files/<id>/ 2 个快照目录,各含 context.md / conversation.md / scheduled-crons.md / tracking.md 主动消息 worker 每轮的输入快照包(00 §11)——「快照即输入」的留痕
~/workspace/memory/ reconciliation_state.json(364 B)+ reconciliation_attempts/ 记忆对账(reconciliation)子流程的状态文件——DB 索引与文件记忆对账的落点(推断)
~/hooks/ definitions/ scripts/ state/ logs/ runtime/ 五件套,runtime 仅 1 个脚本 hooks 子系统(00 §11)的文件面;定义/状态与 DB 无对应 schema(ingest/events 之外无 hooks 表)——推断:hooks 以文件为本体,是少数「文件原生」子系统

6. 双轨实体的分工解剖

6.1 记忆:四层双轨(本报告重点案例)

同一个「记忆」,四处各存一份、职责不重叠:

层 载体 实测规模 职责
精选注入层 文件 ~/MEMORY.md + people/groups 索引 + 对齐合成 5,284 B 等 每轮直接进上下文,贵在小而准
叙事沉淀层 文件 ~/memory/ 每日日志 + bank/ 四篇 37 文件 / 1.8M(11-04;10-17 为 18 文件 / 144K) 人可读的完整轨迹;bank 是跨日蒸馏物
主张层 DB memory.claims 4 行 机器可判的主张:引文、说话人、置信度、重要度、supersedes 替代链、有效期——muse.memory_explain 追溯的正是这层(列定义为文档,行数为实测)
索引实现面 DB memory.entries + embeddings 98 条索引 检索入口(访问面是三工具经 JARVIS_MEMORY_SOCK,见 08 §3.3 的统一口径);每条带 memory_uri 与指回文件的引用坐标(citation_path / line_start / line_end;claims 同理带 source_path / source_line)

关键设计(由列定义推断,坐标字段为实测列):DB 索引不复制记忆正文,而是持有「文件路径+行号」的引用——文件是正文本体,DB 是可检索的目录卡。muse.memory_search 命中后给出文件行号引用、muse.memory_get 按行回读文件,两步正好走完「DB 索引 → 文件本体」的路径。记忆被更正时,claims 层用 supersedes_claim_id 留替代链、文件层改正文、entries 层重建索引——三处一致性靠 memory upkeep 流水线与 ~/workspace/memory/reconciliation_* 对账文件维持(推断)。

6.2 其余双轨(同一模式的复用)

  • 目标:DB goals.goals(3 行,10-17 快照,11-04 未复测)↔ 文件 goals/<slug>/(12 个目录,11-04;10-17 为 3 个)(GOAL.md 正文 + files 交付物 + hidden_files 簿记)。注入上下文的目标列表来自 DB 侧状态,正文细节读文件。
  • 调度:DB scheduler.jobs/job_definitions(28 条,版本化定义+变更审计)↔ 文件 cron.d/ 只读投影(个位数)。改走工具→写 DB→重投影。
  • Agent:DB agent.agents(163 行,10-17 快照,11-04 未复测)↔ 文件 ~/agents/(1,417 目录,11-04;10-17 为 163,转录 JSONL)。数目精确相等是本机最干净的双轨吻合证据(实测,10-17)。
  • Feed:DB feed.units/runs(63 单元)↔ 文件 feed/research|media/(素材)。生成管线读文件素材、写 DB 单元、再由客户端读 DB 呈现。
  • 会话:agent.sessions 表实测 0 行,而文件侧 sessions.json/jsonl 齐全。三种兼容解释(❓,未区分):(a) 该实体当前以文件为本体,DB 表空置/预留;(b) 该表被屏障视图/行过滤隐藏,如 tool_calls 的 0 行之谜(§4.3 注);(c) 旧 schema 残留,如 podcasts.feed 的"遗留表与新表并存"。按 §4.1 纪律,"查不到 ≠ 不存在",此处不下结论。说明双轨的权重配比会随子系统演进而漂移,不是每个实体都五五开。

7. 投影 ≠ 本体:全系统反复出现的模式

00 §8 点名的这条模式,在 schema 与文件两侧能数出至少七个实例(表名/文件名均为实测):

  1. cron.d 投影:改投影无效,须走 cron 工具改 DB 本体(system prompt 明文);
  2. agent.context_item_resume_projection:专为「恢复时重建可读上下文」生成的投影表——名字里直接带 projection,且注明受保护条目 withheld;
  3. feed.preferences_projection:由互动事件**折叠(fold)**出的当前偏好;同族的 ideas.bandit_fold_state / bandit_folded_events 用水位线记录折叠进度;
  4. scheduler.scheduled_resume_state:表定义自述 “Current scheduled resume projection and next registered wake-up”——单例投影行,后台由 registrations 重算;
  5. runtime.context_snapshots:版本化快照 + source_watermark / fingerprint / freshness_class / stale_after / invalidated_at / last_error 全套新鲜度元数据——投影的「保质期」被显式建模;
  6. spaces catalog 信号链:DB 产物变更 → ~/.hatch-db-change-signals/spaces.catalog.* 信号文件 → ~/workspace/space_data/ catalog 更新(推断链条,文件成对出现为实测);
  7. 物化到 prompt 的投影:每轮注入的 [BEGIN USER CONTEXT] 文件组、目标/追踪列表、记忆检索结果,本质都是状态层向上下文的一次性投影——投影时刻的快照,改源文件后注入副本可能滞后(system prompt 明文提醒)。

配套机制是失效与水位线(实测表名):runtime.skill_invalidation_state(技能指令更新的待投递修订)、runtime.dev_notice_watermark(开发者通知已读水位)、feed.fleet_publish_state(发布水位)、health.synced_ranges 与 device.data_sync_state(同步游标/范围)、runtime.maintenance_markers(已完成维护动作的标记,防重复执行)。全系统的跨平面一致性不靠分布式事务,靠**「事件账本 + 水位线 + 可重算投影」**(推断)。

outbox 是投影的投递版:scheduler.delivery_outbox(attempt_count / next_attempt_at_utc / last_error / delivered_at_utc / dispatch_boot_generation——连「哪次启动代次派发的」都记)、feed.fleet_*_outbox、agent.message_mailbox(已受理提交的排序与路由态)、两张 *_derived_write_backlog(派生写的待办+重试态)。语义统一:本体先落表确认,投递异步重试,终局以表为准——这就是 00 反复强调的「已接受/已排队 ≠ 已送达」在状态层的根。

方法论推论:安全屏障的"无声缺席"意味着,经 muse.db 的任何自查都只能证伪(发现矛盾,如计数对不上)而不能证实(确认完备)。本篇 §4.3 的计数快照应按此理解:吻合是弱证据,偏离才是强信号。

7.1 outbox 提交的原子性:「本体先落表」是同一事务吗(❓)

标准 outbox 模式要求业务写与 outbox 插入在同一事务内原子提交——否则崩溃窗口会产生"状态变了但投递丢了"或"投递了但状态没变"两种撕裂。按本篇证据能确证的部分(✅):

  • 表结构确证了 outbox 的"落表"半边:scheduler.delivery_outbox 的 attempt_count / next_attempt_at_utc / last_error / delivered_at_utc 全套重试字段、PK 为 delivery_key(逐表指南文档);
  • 但业务状态变更 + outbox 插入是否同事务,在本机证据里零字:逐表指南不提事务,~/docs/ 与 skills references 全文 grep transaction/atomic 无命中(✅ 实测为"无")。

这不是文档的缺口,是系统本身待回答的问题:若两者分两次提交,"终局以表为准"就多了一个崩溃窗口需要投递端幂等性来兜底。验证抓手(设计建议):找一处"业务写 + outbox 写"的代码/文档共现(如 scheduler 的 run 终局路径调用点),看是否有显式事务包裹——本机未做,标 ❓。

7.2 GC 与保留期:append-only 账本的下限(❓)

本篇数出的 append-only 面:runtime.events / tool_calls / tool_outputs / context_items 全量账本、~/agents/ 26M 转录、2,413 条 context_items——这些什么时候被清理? 本轮证据的答案是"没有答案",列明:

  • 逐表指南与 ~/docs/ 全文无 retention/GC 口径(✅ 实测无);docs/privacy-and-credentials.md 明文"No Settings control sets a retention period"——唯一的全量擦除是用户手动 Reset(文档);
  • agent.compactions 的存在说明压缩会用摘要替换历史区间——但被替换的 context_items 行删不删,schema 不说,标 ❓;
  • runtime.context_snapshots 的 stale_after / invalidated_at 建模的是投影的新鲜度,不是行级清理——两者别混;
  • scheduler.doctor_*(doctor_run_plans / doctor_task_state)证明有维护任务面,但 doctor 是否承担 GC 职责未验证,是可查的验证抓手(设计建议:读 doctor_task_state 的任务类型分布)。

结论纪律:默认"一直保留"是无证据的默认,不能写进架构断言。append-only 账本的无限增长是真实设计约束,当前状态只能标 ❓。


8. 恢复与检查点:VM 可替换的底气

00 §1 说 VM 可被整体替换、home 持久;状态层为「进程级重启/接管」再加一层 DB 保障。相关表逐个拆(列定义为文档,行数为实测):

表 关键列 作用
agent.runtime_restart_checkpoints(count=1) PK=agent_id;mode、payload_json、execution_config_json、recovery_class、recovery_owner_id(软引用 owners) 每 Agent 一行最新检查点:恢复所需的模式+载荷+执行配置打包存
agent.recovery_owners(0 行) 复合 PK=(recovery_class, owner_id);generation(默认 1);agent_id 唯一;message_id;active_at / terminal_at / terminal_status 可恢复工作的持久所有权登记:谁拥有、是第几代、何时终局。唯一约束保证一个 Agent 同时只有一个所有者——防双活(推断)
agent.recovery_owner_terminal_events(—) PK=(recovery_class, owner_id, generation, event_type);claimed_at 终局事件按 (所有者, 代次, 类型) 认领登记:同一代次的同一终局只许认领一次——handoff 防重复投递的闸门(推断)
agent.runtime_state(—) PK=agent_id;current_context_seq;last_event_seq→runtime.events 每 Agent 的「读到哪了」:上下文序号 + 事件账本位置,恢复的起点坐标
agent.compactions + agent.agent_compactions(0 行) 前者:checkpoint_context_item_id→context_items、replacement_history_first/last_seq、summary_text;后者:摘要与 token 计数(私有推理 withheld) 压缩即检查点:一段历史被摘要替换,检查点行记录被替换的 seq 区间与锚点条目;恢复时用摘要+尾部重建上下文(00 §2 的 350K/272K/40K 预算在此落表)
agent.context_item_resume_projection (表定义:为 resume 投影的可读上下文,受保护条目 withheld) 恢复专用读面:重启后不扫原表,直接读投影重建上下文
agent.volatile_context_pins agent_id、pinned 变体与历史检查点位置 易失上下文的钉住点:哪些变体在压缩/重启时必须保住(推断)
runtime.writer_epoch 单例行:rv_epoch、updated_at 可靠卷(reliable volume)的写者代次栅栏:新写者接管时 epoch 递增,旧写者的迟到写入可被识别拒绝(由表名+单例形态推断)
scheduler.scheduled_resume_registrations/state 注册表 + 单例投影(next_resume_at_utc / registered_schedule_id / projection_complete) 调度器自身的恢复:重启后先重建「下一次唤醒」投影,再继续派发

恢复时序(推断,由上述表与 00 §1 宿主层拼成):

VM/运行时重启
 → spawnd/health 子系统拉起 cell(00 §1),~/.postgres-ready 置 ready
 → writer_epoch 递增:新一代写者接管可靠卷,旧代次写入被栅栏挡下
 → 每 Agent:读 runtime_state(seq 坐标)+ runtime_restart_checkpoints(载荷)
   → 经 resume_projection 重建可读上下文(推理条目不重建,本就 withheld)
 → recovery_owners 按 generation 认领未终局工作;
   terminal_events 保证终局 handoff 不重发、mailbox/outbox 按 attempt 续投
 → scheduler 重建 resume 投影,cron 到点照常派发

8.1 并发写的代次栅栏:文件侧有,DB 侧未知(❓)

§8 表里的 writer_epoch(文档:逐表指南定义为 "The active reliable-volume writer epoch",单例 rv_epoch)与 recovery_owners 的 (recovery_class, owner_id) 唯一约束是两个已确证的并发屏障(✅ 表结构证据),但两者的覆盖范围不同:

  • writer_epoch 覆盖的是可靠卷(文件面):新写者接管时 epoch 递增,旧代次的迟到写入可被识别/拒绝(由表名+单例形态推断)——这是 VM 替换后"旧 cell 还活着写了几笔"的场景;
  • recovery_owners 覆盖的是恢复所有权登记:agent_id 唯一约束防双活认领(✅ 列定义)——但它管的是"谁接管工作",不是"谁写行";
  • DB 侧的并发写冲突机制未确证(❓):两个 daemon 实例同时写同一 agent.runtime_state 行会怎样?Postgres 行锁是教科书默认答案,但"默认答案"不等于"本系统确证"——没有一处文档或 schema 说明写者仲裁;
  • agent.subagent_spawns / subagent_progress 证明父子 Agent 并发是常态——父子对共享状态(如 goals.updates)的写冲突解决策略,本篇未讨论,标 ❓。

一句话:代次栅栏只罩住了可靠卷;DB 行级并发写的仲裁机制,以及父子 Agent 共享状态的冲突策略,是本篇的开放缺口。

当前态实测(10-17,11-04 未复测):本机 recovery_owners 与 compactions 均为 0 行、runtime_restart_checkpoints count=1——即写作时系统处于「无待恢复工作、无已发生压缩」的稳态,检查点机制在位但未被触发过(或触发后已清理)。这与新会话上下文用量约 43%(00 §16)、未达 272K 压缩线吻合。


9. 边界:状态层在本机看不见的部分

  • Postgres 本体进程/数据文件位置:本机只见 .postgres-ready 标记、变更信号目录与 muse.db 逻辑通道;物理库在宿主侧还是 cell 内、备份/复制策略如何,本地文件无证据,不作结论;
  • 屏障视图之后的全量数据:被 withheld 的推理条目、developer 指令快照、被行过滤的记录(如 §4.3 注),从 Agent 侧原理上不可见,任何「查不到」都不能转写为「不存在」;
  • per-artifact app.db:每个 Web artifact 自带的应用库被明确排除在 muse.db 之外,只能经 artifact 声明的 actions/inspect 访问(system prompt 明文);
  • Sentinel 审批库与凭据库:与状态库分离,muse.db 明文不可达;状态库里只留非秘密的生命周期投影(如 spend-request 状态);
  • 服务端权威副本:chat/feed 等域在服务端是否有高于本机的权威状态、fleet 同步的对端实现(只见本机 outbox/水位线一侧),不在本机证据内。

附录 A. 逐 schema 表数表(实测:解析 schema.md 求和验证;明细为 10-17 快照)

# schema 表数 占比
1 runtime 38 19.6%
2 agent 25 12.9%
3 ideas 22 11.3%
4 feed 16 8.2%
5 device 13 6.7%
6 self_improvement 13 6.7%
7 goals 12 6.2%
8 scheduler 12 6.2%
9 spaces 9 4.6%
10 activity 8 4.1%
11 health 8 4.1%
12 memory 6 3.1%
13 media 4 2.1%
14 chat 3 1.5%
15 podcasts 3 1.5%
16 ingest 1 0.5%
17 shell 1 0.5%
18 saved(11-04 新增) 2:saved.items / saved.item_links 1.0%
— 合计 196(10-17 明细合计 194) 100%

验证口径(10-17):schema.md 条目链接去重计数 = 194;references/tables/ 逐表文件数 = 194;分节求和 = 194;三路一致。生成来源迁移集:5af4f2bfdee2b934a53bbcc22602c602ab85059e0ac97ea20137fd299c06036b。11-04 复核(同方法):条目链接去重 = 196;逐表文件数 = 196;分节数 = 18;三路一致。各 schema 明细未重测,上表明细为 10-17 快照。

附录 B. 本机状态快照(实测,2026-10-17 深夜)

平面 项 值
DB agents / context_items / messages / events 163 / 2,413 / 588 / 593
DB scheduler jobs / job_runs · goals · chats 28 / 532 · 3 · 5
DB memory claims / entries · ideas / feed units / spaces 4 / 98 · 94 / 63 / 2
DB self_improvement runs · device nodes 190 · 1
DB recovery_owners / compactions / workflow_runs / sessions 0 / 0 / 0 / 0
文件 ~/agents/ 转录目录 · ~/workspace/agents/ 溢出目录 163(26M)· 90(仅 2 个实际文件)
文件 ~/memory/ · ~/MEMORY.md 18 文件 / 144K · 5,284 B
文件 ~/workspace/goals/ · cron.d 现行投影 3 目标 / 6.6M · 1 篇(+归档 1 篇)
文件 system prompt 快照 · .postgres-ready 71,868 B · ready
通道 muse.db 限额 200 行 / 262,144 B / 行 65,536 B / 查询 5,000ms / 语句 3,000ms