Skip to content

fix(trading): commit account state before projections - #41

Merged
kunkundi merged 3 commits into
kunkundi:mainfrom
CyrusAuyeung:codex/fix-practice-state-commit-order
Aug 25, 2026
Merged

fix(trading): commit account state before projections#41
kunkundi merged 3 commits into
kunkundi:mainfrom
CyrusAuyeung:codex/fix-practice-state-commit-order

Conversation

@CyrusAuyeung

@CyrusAuyeung CyrusAuyeung commented Aug 18, 2026

Copy link
Copy Markdown
Contributor

修改内容

  • 将直接模型成交、延迟成交、自动离场和单独决策日志统一调整为“先保存规范账户 JSON,再写 SQLite 投影”;账户保存失败时不再写入成交、决策、持仓快照,也不发送成交通知。
  • 抽取已提交账户投影同步入口,保持成交、决策、持仓快照及耐久证据状态的原有返回语义。
  • 将账户历史压缩改为安全的两阶段提交:先原子保存包含完整历史的 JSON,再归档到 SQLite;归档成功后才压缩 JSON。压缩替换失败时保留已经提交的完整 JSON,后续保存可自动重试。
  • 为原子写入补充临时文件清理,避免失败路径残留临时状态文件。
  • 容器入口会创建 cron/output,并在启动 Dashboard/Scheduler 前检查关键运行目录、账户 JSON 和数据库文件的读写权限;bind mount 所有权错误会以明确诊断提前失败。
  • 补充直接成交、延迟成交、自动离场、决策日志、历史归档提交顺序、压缩降级和容器权限预检回归测试。

问题原因

账户 JSON 是现金与持仓的规范状态,但多个成交路径此前会先写 SQLite 的 tradesdecisionsposition_snapshots,最后才调用 save_state。如果 JSON 因 bind mount 所有权或其他 I/O 错误无法原子替换,前面的数据库写入已经提交,导致 SQLite 出现账户 JSON 中不存在的孤立成交。

save_state 自身也会先归档完整历史,再替换 JSON,因此同一故障还可能提前暴露未提交的账户历史。容器入口没有创建账户输出目录或验证关键路径权限,使权限问题延迟到交易执行时才被发现。

兼容性与影响范围

  • 不改变成交价格、费用、T+1、策略阈值、仓位、风险预算、候选筛选或任何交易精度。
  • 正常保存时仍写入相同的 JSON、SQLite 结构化表、追加式账户历史和持仓快照;仅调整提交顺序与失败边界。
  • 历史归档失败时继续保留完整 JSON;归档成功但压缩失败时同样保留完整 JSON,不丢失任何历史。
  • 保持定时自动离场、决策前自动离场、延迟成交和直接决策入口的返回字段及通知行为。
  • 权限正常的命名卷和 bind mount 行为不变;权限错误的容器会更早、以明确错误停止。
  • 不新增第三方依赖。

Fixes #40

验证结果

  • git rebase origin/main:已无冲突重放到最新主线 441a547,补丁提交为 f019f06
  • git diff --check origin/main...HEAD:通过。
  • bash -n scripts/docker-entrypoint.sh:通过。
  • 本地账户计账、通知钩子、自动离场/并发规则、账户历史迁移和容器部署相关测试共 158 项:156 项通过、1 项跳过;唯一失败是 Windows 路径分隔符断言,已在未修改的当前 origin/main 单独复现。
  • ./scripts/validate.sh:Python/JavaScript/Shell/BAT 语法检查与 Vue 生产构建通过;共运行 1424 项单元测试,Windows 环境下为 4 个失败、4 个错误、1 个跳过,均属于既有的路径分隔符、POSIX 权限断言和 SQLite 临时文件锁类别,本分支任务相关测试未新增失败。
  • Linux Python 3.11 镜像内运行账户提交顺序、交易通知、历史迁移、容器权限、牛牛策略及本次上游策略变更相关测试:388 项全部通过。
  • docker build --build-arg PYTHON_VERSION=3.11:通过。

@CyrusAuyeung
CyrusAuyeung force-pushed the codex/fix-practice-state-commit-order branch from bcd9dfb to e420255 Compare August 18, 2026 10:13
@CyrusAuyeung
CyrusAuyeung force-pushed the codex/fix-practice-state-commit-order branch from e420255 to f019f06 Compare August 21, 2026 12:55
@kunkundi
kunkundi merged commit 03aa334 into kunkundi:main Aug 25, 2026
2 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

[Bug] 模拟账户状态保存失败时会提前写入 SQLite 并留下孤立成交

2 participants