CocoAudit — 会话审计追踪
概述
CocoAudit 读取位于 lifecycle/audit.md 的仅追加审计追踪。每一次计划审批、规格门禁通过、$ship 确认、SecondEye 确认以及 CocoSentinel 审批都会被逐字记录,并附带 ISO 8601 UTC 时间戳。该记录在项目生命周期内从不被摘要、从不被覆盖、从不被删除。
启用 CocoAudit
在 $pod init 时启用,开发者需选择“Enable session audit trail? (recommended for regulated environments)”。这会创建 modes/cocoaudit.on 并使用项目头部初始化 lifecycle/audit.md。
CocoContract 生命周期事件(Feature 44 增强)
CocoAudit 记录四类 CocoContract 事件,由 contract-prove 以及 .cortex/skills/cococontract/contract/SKILL.md 的归档步骤通过 PostToolUse 钩子已使用的同一 lifecycle/audit.md 追加逻辑写入:
- 合约声明:新结果合约的全文(persona、可观察结果、可证伪条件),以及声明的会话 ID 和时间戳。
- 证据提交:证据层级(e2e / reference / spec / differential / unit)、提交时的函数版本哈希、结果(通过/失败)以及逐字证据描述。
- 过期证据检测:当先前通过的证据检查因函数版本变更而被发现过期时记录:先前通过的版本哈希、当前版本哈希以及检测时间戳。
- 合约归档:当合约被提交到 outcomes/ 时记录,并附带合约内容哈希。
$audit ci
在标准审计日志校验之前扩展 $audit,增加一个合约回归阶段。调用 audit-ci。回归阶段读取 outcomes/ 中所有已归档合约,在可机器执行的情况下重新执行每个合约的可证伪条件(针对真实 Cortex 端点的 e2e 检查),并记录通过/失败。重新执行失败的合约即为行为回归——以与失败安全门禁相同的严重级别报告。旨在用作 CI/CD 部署前门禁。
命令
$audit add "<message>"
路由到 .cortex/skills/cocoaudit/audit-add/SKILL.md。使用以下方式追加一个清晰标记的手动事件:
invoke audit-events add "<message>"
手动条目适用于迁移、测试和文档场景。它们必须保持标记为手动,且不得被视为钩子生成的 HITL 证据。
$audit timeline
路由到 .cortex/skills/cocoaudit/audit-timeline/SKILL.md。使用以下方式显示紧凑的时间顺序视图:
invoke audit-events timeline
$audit view [--from <date>]
步骤:
- 检查 modes/cocoaudit.on 是否存在——若不存在,输出:“CocoAudit is not enabled. Enable at $pod init or create modes/cocoaudit.on manually.”
- 检查 lifecycle/audit.md 是否存在——若不存在,输出:“Audit trail not yet initialized. Run $pod init with audit enabled.”
- 读取 lifecycle/audit.md 并解析 ## [Event Type] 头部块
- 若提供了 --from 过滤器则应用:将每个块的 Timestamp 字段解析为 ISO 8601 UTC 时间戳,并包含时间戳大于或等于过滤值的事件。仅日期过滤器如 2026-06-01 表示 2026-06-01T00:00:00Z。
- 无过滤器:显示最后 20 个块;有过滤器:显示所有匹配块
- 以终端格式渲染:
──────────────────────────────────────── [plan-approved] 2026-06-14T10:30:00Z Artifact: lifecycle/plan.md Input: "looks good, proceed" Result: Build phase unlocked ────────────────────────────────────────
- 显示总数:“Showing N of M total audit events”
$audit export
步骤:
- 检查 modes/cocoaudit.on 是否存在
- 检查 lifecycle/audit.md 是否存在
- 统计文件中 ## [ 事件块的总数
- 生成带时间戳的文件名:audit-export-YYYY-MM-DDTHH-MM-SSZ.md(冒号替换为连字符以确保文件系统安全)
- 写入 .cocoplus/audit-export-[timestamp].md:
CocoAudit — Compliance Export
Project: [project name from lifecycle/meta.json] Exported: [ISO 8601 UTC timestamp] Total Events: [N]
This document is an append-only audit trail. Records are verbatim developer inputs. This file must not be edited after export.
[Full verbatim content of lifecycle/audit.md]
- 输出:“Audit export written to .cocoplus/audit-export-[timestamp].md ([N] events)”
幂等:每次调用生成一个新的带时间戳文件。从不覆盖先前的导出。
完整性检查
在查看、导出或运行 $audit ci 时,在渲染前验证审计结构:
- 每个事件块以 ## [ 开头,并包含 Timestamp 和 Event
- 时间戳可解析为 ISO 8601 UTC
- 事件块保持时间戳非递减顺序
- 格式错误的块会报告其块编号和首个标题行
检查完整性时不要修改 audit.md。允许报告格式错误的审计结构;修复仅追加文件需要开发者明确指示。
退出标准
- 无 --from 过滤器时,$audit view 正确渲染最后 20 个事件
- $audit view --from 2026-06-01 仅显示该日期起的事件
- $audit view 在渲染前报告格式错误或乱序的事件块
- $audit export 每次调用生成唯一的带时间戳文件
- 当 modes/cocoaudit.on 缺失时,两个命令均以清晰错误优雅失败
- 当 lifecycle/audit.md 缺失时,两个命令均优雅失败
- 所有四类 CocoContract 事件(声明、证据提交、过期证据检测、归档)均被记录并被 $audit view 识别
- $audit ci 在标准审计日志校验前运行合约回归阶段,并在任何回归时以非零退出
反合理化
诱惑 | 为何错误
摘要开发者输入 | 逐字是要求——改写会破坏审计有效性
覆盖先前导出 | 幂等意味着每次新文件,而非同一文件
在时间戳中使用本地时区 | 仅 ISO 8601 UTC——本地时区时间戳不是审计级
删除或截断 audit.md | 仅追加意味着从不删除;它是合规工件
自动修复格式错误的审计块 | 审计修复会改变合规证据,需要开发者明确指示