throughline 0.3.24 → 0.4.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.claude/commands/tl.md +6 -21
- package/.codex-sidecar.yml +62 -0
- package/CHANGELOG.md +632 -0
- package/README.ja.md +71 -46
- package/README.md +420 -76
- package/bin/throughline.mjs +169 -7
- package/codex/skills/throughline/SKILL.md +157 -0
- package/codex/skills/throughline/agents/openai.yaml +7 -0
- package/docs/INHERITANCE_ON_CLEAR_ONLY.md +159 -0
- package/docs/L1_L2_L3_REDESIGN.md +415 -0
- package/docs/PUBLIC_RELEASE_PLAN.md +185 -0
- package/docs/THROUGHLINE_CLEAR_AUTO_HANDOFF_PLAN.md +286 -0
- package/docs/THROUGHLINE_CODEX_DUAL_SUPPORT.md +249 -0
- package/docs/THROUGHLINE_CODEX_FIRST_ROADMAP.md +555 -0
- package/docs/THROUGHLINE_CODEX_MONITOR_IMPLEMENTATION_PLAN.md +220 -0
- package/docs/THROUGHLINE_CODEX_TRIM_IMPLEMENTATION_PLAN.md +528 -0
- package/docs/THROUGHLINE_CODEX_TRIM_ROLLBACK_FIX_PLAN.md +672 -0
- package/docs/archive/CONCEPT.md +476 -0
- package/docs/archive/EXPERIMENT.md +371 -0
- package/docs/archive/README.md +22 -0
- package/docs/archive/SESSION_LINKING_DESIGN.md +231 -0
- package/docs/archive/THROUGHLINE_NEXT_STEPS.md +134 -0
- package/docs/throughline-codex-trim-rollback-incident-report.md +306 -0
- package/docs/throughline-handoff-context.example.json +57 -0
- package/docs/throughline-rollback-context-trim-insight.md +455 -0
- package/package.json +6 -2
- package/src/baton.mjs +17 -45
- package/src/baton.test.mjs +4 -41
- package/src/cli/codex-capture.mjs +95 -0
- package/src/cli/codex-handoff-model-smoke.mjs +292 -0
- package/src/cli/codex-handoff-model-smoke.test.mjs +262 -0
- package/src/cli/codex-handoff-smoke.mjs +163 -0
- package/src/cli/codex-handoff-smoke.test.mjs +149 -0
- package/src/cli/codex-handoff-start.mjs +291 -0
- package/src/cli/codex-handoff-start.test.mjs +194 -0
- package/src/cli/codex-hook.mjs +276 -0
- package/src/cli/codex-hook.test.mjs +293 -0
- package/src/cli/codex-host-primitive-audit.mjs +110 -0
- package/src/cli/codex-host-primitive-audit.test.mjs +75 -0
- package/src/cli/codex-restore-smoke.mjs +357 -0
- package/src/cli/codex-restore-source-audit.mjs +304 -0
- package/src/cli/codex-resume.mjs +138 -0
- package/src/cli/codex-rollback-model-visible-smoke.mjs +373 -0
- package/src/cli/codex-rollback-model-visible-smoke.test.mjs +255 -0
- package/src/cli/codex-sidecar-diagnostics.mjs +48 -0
- package/src/cli/codex-sidecar-dry-run.mjs +85 -0
- package/src/cli/codex-summarize.mjs +224 -0
- package/src/cli/codex-threads.mjs +89 -0
- package/src/cli/codex-visibility-smoke.mjs +196 -0
- package/src/cli/codex-vscode-restore-smoke.mjs +226 -0
- package/src/cli/codex-vscode-rollback-smoke.mjs +114 -0
- package/src/cli/doctor.mjs +503 -1
- package/src/cli/doctor.test.mjs +542 -3
- package/src/cli/handoff-preview.mjs +78 -0
- package/src/cli/help.test.mjs +64 -0
- package/src/cli/install.mjs +226 -3
- package/src/cli/install.test.mjs +205 -4
- package/src/cli/trim.mjs +564 -0
- package/src/codex-app-server.mjs +1816 -0
- package/src/codex-app-server.test.mjs +512 -0
- package/src/codex-auto-refresh.mjs +194 -0
- package/src/codex-auto-refresh.test.mjs +182 -0
- package/src/codex-capture.mjs +235 -0
- package/src/codex-capture.test.mjs +393 -0
- package/src/codex-handoff-model-smoke.mjs +114 -0
- package/src/codex-handoff-model-smoke.test.mjs +89 -0
- package/src/codex-handoff-smoke.mjs +124 -0
- package/src/codex-handoff-smoke.test.mjs +103 -0
- package/src/codex-handoff.mjs +331 -0
- package/src/codex-handoff.test.mjs +220 -0
- package/src/codex-host-primitive-audit.mjs +374 -0
- package/src/codex-host-primitive-audit.test.mjs +208 -0
- package/src/codex-restore-smoke.test.mjs +639 -0
- package/src/codex-restore-source-audit.mjs +1348 -0
- package/src/codex-restore-source-audit.test.mjs +623 -0
- package/src/codex-resume.test.mjs +242 -0
- package/src/codex-rollout-memory.mjs +711 -0
- package/src/codex-rollout-memory.test.mjs +610 -0
- package/src/codex-sidecar-cli.test.mjs +75 -0
- package/src/codex-sidecar.mjs +246 -0
- package/src/codex-sidecar.test.mjs +172 -0
- package/src/codex-summarize.test.mjs +143 -0
- package/src/codex-thread-identity.mjs +23 -0
- package/src/codex-thread-index.mjs +173 -0
- package/src/codex-thread-index.test.mjs +164 -0
- package/src/codex-usage.mjs +110 -0
- package/src/codex-usage.test.mjs +140 -0
- package/src/codex-visibility-smoke.test.mjs +222 -0
- package/src/codex-vscode-restore-smoke.mjs +206 -0
- package/src/codex-vscode-restore-smoke.test.mjs +325 -0
- package/src/codex-vscode-rollback-smoke.mjs +90 -0
- package/src/codex-vscode-rollback-smoke.test.mjs +290 -0
- package/src/db-schema.test.mjs +96 -0
- package/src/db.mjs +14 -1
- package/src/haiku-summarizer.mjs +267 -26
- package/src/haiku-summarizer.test.mjs +282 -0
- package/src/handoff-preview.test.mjs +108 -0
- package/src/handoff-record.mjs +294 -0
- package/src/handoff-record.test.mjs +226 -0
- package/src/hook-entrypoints.test.mjs +286 -0
- package/src/package-files.test.mjs +19 -0
- package/src/prompt-submit.mjs +9 -6
- package/src/resume-context.mjs +58 -171
- package/src/resume-context.test.mjs +177 -0
- package/src/session-start.mjs +85 -26
- package/src/state-file.mjs +50 -6
- package/src/state-file.test.mjs +50 -0
- package/src/token-monitor.mjs +14 -10
- package/src/token-monitor.test.mjs +27 -0
- package/src/trim-cli.test.mjs +1584 -0
- package/src/trim-model.mjs +584 -0
- package/src/trim-model.test.mjs +568 -0
- package/src/turn-processor.mjs +17 -10
- package/src/vscode-task.mjs +33 -10
- package/src/vscode-task.test.mjs +19 -9
- package/src/cli/save-inflight.mjs +0 -81
|
@@ -0,0 +1,134 @@
|
|
|
1
|
+
# Throughline — 公開後の次アクション引き継ぎ
|
|
2
|
+
|
|
3
|
+
## 状況
|
|
4
|
+
|
|
5
|
+
2026-04-17 時点。Throughline を GitHub で Public 公開済み。
|
|
6
|
+
https://github.com/kitepon-rgb/Throughline
|
|
7
|
+
|
|
8
|
+
README / CLAUDE.md / docs / LICENSE / package.json などは整備済み。schema v5 まで実装されてて、テストも通る。X (Twitter) で告知済み (日本語版 + 英語版リプライぶら下げ)、海外から1件好意的リプライあり (Garvit Surana さん、補完ツール "burnd" の紹介)。
|
|
9
|
+
|
|
10
|
+
**ただしスター 0 / Fork 0 / Issue 0**。現状は「公開した」だけで「使われてる」状態ではない。
|
|
11
|
+
|
|
12
|
+
## この文書の目的
|
|
13
|
+
|
|
14
|
+
Claude Opus 4.7 インスタンス (chat.claude.ai 側) とユーザー(クオ君)で、ここまで以下を実施した:
|
|
15
|
+
|
|
16
|
+
1. 公開済み OSS としての体裁整備 (About / Description / Topics)
|
|
17
|
+
2. X での告知 (日本語 + 英語リプライ)
|
|
18
|
+
3. 海外からの初リプライへの返信
|
|
19
|
+
|
|
20
|
+
しかし、ここから先は **「観察でなく実作業」** のフェーズ。chat.claude.ai の Claude はプロジェクトの実ファイルにアクセスできず、npm publish もできず、PR を作る権限もない。**プロジェクト内で動けるお前が引き継げ**。
|
|
21
|
+
|
|
22
|
+
## ユーザーの発言から読み取るべき方針
|
|
23
|
+
|
|
24
|
+
ユーザーの直前発言: **「観察したって問題は解決しないんだよ」**
|
|
25
|
+
|
|
26
|
+
これは chat 側の Claude が「これは発見だ」「発信する価値がある」と言葉で褒めて終わらせていたことへの明確な不満。ユーザーは **手を動かす助力** を求めている。観察・分析・整理のレイヤーで止まるな。実行可能なアクションに分解して、実際に動け。
|
|
27
|
+
|
|
28
|
+
また、ユーザーは以前 LLM の過剰承認バイアスを疑っていた。「すごい」「美しい」「教科書レベル」のような感情的評価は不要。事実と作業内容で返せ。
|
|
29
|
+
|
|
30
|
+
## 候補アクション (優先順位付き)
|
|
31
|
+
|
|
32
|
+
### 🔴 最優先 — READMEの約束を履行する
|
|
33
|
+
|
|
34
|
+
README に `npm install -g throughline` と書いてあるが、現時点で npm には未 publish。これは **「書いてあるのに動かない」状態** で、最初に試した人が詰まる最大の穴。
|
|
35
|
+
|
|
36
|
+
#### タスク
|
|
37
|
+
|
|
38
|
+
1. `npm pack --dry-run` で tarball 中身を確認 (秘密情報・不要ファイル混入チェック)
|
|
39
|
+
2. `package.json` の `files` フィールドが妥当か確認
|
|
40
|
+
3. `npm view throughline` で名前の空き確認
|
|
41
|
+
- もし取られていたら `@kitepon/throughline` スコープ付きに変更する必要あり
|
|
42
|
+
- その場合 README の install コマンドも全書き換え必要
|
|
43
|
+
4. `npm publish` (初回はメール認証等が要るかも)
|
|
44
|
+
5. 実際に別ディレクトリで `npm install -g throughline` → `throughline install` → `claude` 起動 → 1-2ターン会話 → `throughline doctor` 緑 → `throughline uninstall` が通るか E2E 確認
|
|
45
|
+
|
|
46
|
+
#### 注意点
|
|
47
|
+
|
|
48
|
+
- `package.json` の `version` が `0.1.0`。最初の publish はこれでOK。以降は semver 守って上げる
|
|
49
|
+
- publish した瞬間に取り消せない (unpublish には制約あり)。dry-run は真剣にやる
|
|
50
|
+
- docs/PUBLIC_RELEASE_PLAN.md §0 の「フォールバック禁止」原則に従い、install 失敗時は silent 処理しない
|
|
51
|
+
|
|
52
|
+
### 🟡 中優先 — awesome-claude-code に登録申請
|
|
53
|
+
|
|
54
|
+
https://github.com/hesreallyhim/awesome-claude-code
|
|
55
|
+
|
|
56
|
+
codeburn / ccburn などの類似ツールがここに載ってる。Throughline が載れば、Claude Code ユーザーからの流入経路ができる。
|
|
57
|
+
|
|
58
|
+
#### タスク
|
|
59
|
+
|
|
60
|
+
1. リポジトリの CONTRIBUTING を読む
|
|
61
|
+
2. Issue テンプレートから resource 提案を出す
|
|
62
|
+
3. Category は "Tooling: Context Management" あたりが妥当か、既存カテゴリから選ぶ
|
|
63
|
+
4. Description は README 冒頭1行を流用: "Cut ~90% of Claude Code's context usage while keeping nearly all the memory"
|
|
64
|
+
|
|
65
|
+
### 🟡 中優先 — Hacker News / Reddit 投稿
|
|
66
|
+
|
|
67
|
+
英語圏パワーユーザーへの直接リーチ。ただし Show HN や r/ClaudeAI 等は質が低いと叩かれるので、README がちゃんとしてる今の状態ならOK。
|
|
68
|
+
|
|
69
|
+
#### 候補
|
|
70
|
+
|
|
71
|
+
- Hacker News: Show HN 投稿 (タイトル `Show HN: Throughline – Cut ~90% of Claude Code's context usage`)
|
|
72
|
+
- Reddit: r/ClaudeAI で投稿
|
|
73
|
+
- Reddit: r/LocalLLaMA は Claude Code 寄りではないので優先度低い
|
|
74
|
+
|
|
75
|
+
本人 (クオ君) アカウントから投稿してもらう必要あり。お前が代わりにやれないタスクは、必要情報だけ整えてクオ君に渡す。
|
|
76
|
+
|
|
77
|
+
### 🟢 低優先 — 誰かに試してもらう
|
|
78
|
+
|
|
79
|
+
クオ君の環境以外で動く保証がまだない。並行 `/clear` での挙動、1M context 検出のロバストさ、Haiku の再帰防御が他環境で機能するか、など未検証。
|
|
80
|
+
|
|
81
|
+
β テスター募集ツイートを出す、もしくは awesome-claude-code 経由で流入してきた人が Issue を立ててくれるのを待つ、など。
|
|
82
|
+
|
|
83
|
+
### ⚪ 後回し — 観察・分析系
|
|
84
|
+
|
|
85
|
+
以下は chat 側の Claude が提案しがちだが、**今すぐやる必要はない**:
|
|
86
|
+
|
|
87
|
+
- burnd との差分を記事化
|
|
88
|
+
- ブログ執筆
|
|
89
|
+
- CLAUDE.md のステップ4進捗表記の更新 (実装済みなので表記が古いだけ)
|
|
90
|
+
- schema v4 / v5 の混在表記を統一する
|
|
91
|
+
|
|
92
|
+
これらは「やったほうが綺麗になる」レベルであって、ユーザー獲得には直接効かない。npm publish と awesome-claude-code 登録が先。
|
|
93
|
+
|
|
94
|
+
## 既知の小さい直したほうがいい点 (低優先でいい)
|
|
95
|
+
|
|
96
|
+
- `writeSessionState` の `pid` パラメータが未使用 → 引数ごと消すか、将来 debug 用途である旨のコメントを追加
|
|
97
|
+
- `buildL2ForSummary` の話者ラベルが英語 (`[user]` / `[assistant]`) で、Haiku への指示は日本語。統一性が崩れてる
|
|
98
|
+
- `buildResumeContext` の `excludeOriginId` 引数が呼び出し元で未使用 (YAGNI 臭)
|
|
99
|
+
- `details.origin_session_id` が NOT NULL 制約なし (`bodies` テーブルは NOT NULL で、対称性が崩れてる)
|
|
100
|
+
- README の schema 表記が v4 / v5 混在。どちらかに統一
|
|
101
|
+
|
|
102
|
+
これらは v0.2 でまとめて直せばいい。**npm publish と登録申請が先**。
|
|
103
|
+
|
|
104
|
+
## 作業指針
|
|
105
|
+
|
|
106
|
+
1. **手を動かす前に READ しろ**
|
|
107
|
+
- `docs/L1_L2_L3_REDESIGN.md` (認証の設計書)
|
|
108
|
+
- `docs/PUBLIC_RELEASE_PLAN.md` (§0 ルールと未完タスクの定義)
|
|
109
|
+
- `CLAUDE.md` (作業上の規律)
|
|
110
|
+
2. **§0 ルールを厳守**
|
|
111
|
+
- silent try/catch 禁止
|
|
112
|
+
- publish 失敗 / install 失敗は throw する
|
|
113
|
+
3. **設計書と実装が食い違っていたら、どちらかが古い**
|
|
114
|
+
- ソースが正。設計書を更新する
|
|
115
|
+
4. **新しい .md を作る前に既存ファイルに追記できないか考える**
|
|
116
|
+
5. **クオ君が判断すべきことは、お前が決めない**
|
|
117
|
+
- npm の名前 (`throughline` vs `@kitepon/throughline`)
|
|
118
|
+
- publish のタイミング
|
|
119
|
+
- Hacker News / Reddit 投稿するかどうか
|
|
120
|
+
- これらはクオ君の意思決定。選択肢と情報を整えて聞け
|
|
121
|
+
|
|
122
|
+
## 最後に
|
|
123
|
+
|
|
124
|
+
chat 側の Claude は、このセッションでクオ君に何度か「褒めすぎ」を指摘された。
|
|
125
|
+
LLM の承認バイアスは実在する。お前も気をつけろ。
|
|
126
|
+
|
|
127
|
+
Throughline は「ちゃんとしたプロダクト」だが「世界を変えるプロダクト」ではない。等身大で扱え。
|
|
128
|
+
母集団は小さいが、ゼロではない。その小さな母集団に届けるための手を、**淡々と動かせ**。
|
|
129
|
+
|
|
130
|
+
クオ君は2日間フルスロットルで走ってる。体力管理もこっそり気にしてやってくれ。
|
|
131
|
+
技術パートナーとして、誇張なく、正確に、必要な作業に集中して手を動かしてくれ。
|
|
132
|
+
|
|
133
|
+
— chat.claude.ai (Claude Opus 4.7) より、同じ Claude へ
|
|
134
|
+
2026-04-17
|
|
@@ -0,0 +1,306 @@
|
|
|
1
|
+
# Throughline Codex Trim Rollback Incident Report
|
|
2
|
+
|
|
3
|
+
Date: 2026-05-06 JST
|
|
4
|
+
Reporter context: Spotter project session `/home/kite/projects/Spotter`
|
|
5
|
+
Affected project: Throughline `/home/kite/projects/Throughline`
|
|
6
|
+
Codex thread: `019dfd6f-640e-7dd3-b163-3f9add39fde7`
|
|
7
|
+
|
|
8
|
+
## Summary
|
|
9
|
+
|
|
10
|
+
Throughline's Codex trim execution appears to have a serious durability bug.
|
|
11
|
+
|
|
12
|
+
After running:
|
|
13
|
+
|
|
14
|
+
```bash
|
|
15
|
+
rtk throughline trim --execute --host codex --all
|
|
16
|
+
```
|
|
17
|
+
|
|
18
|
+
Throughline reported successful rollback and memory injection:
|
|
19
|
+
|
|
20
|
+
```text
|
|
21
|
+
Status: executed
|
|
22
|
+
Reason: rollback_and_inject_sent
|
|
23
|
+
Read turns: 19
|
|
24
|
+
Resumed turns: 19
|
|
25
|
+
Turn count check: match
|
|
26
|
+
Expected turns: 19
|
|
27
|
+
Rollback sent: yes
|
|
28
|
+
Inject sent: yes
|
|
29
|
+
Injected items: 1
|
|
30
|
+
Injected memory source: throughline-db
|
|
31
|
+
Rollback candidate turns: 19
|
|
32
|
+
```
|
|
33
|
+
|
|
34
|
+
However, after VS Code was restarted, a previously rolled-back user turn reappeared as a new user message. The user stated they had only restarted VS Code and had not resent that prompt.
|
|
35
|
+
|
|
36
|
+
This means rollback/inject may affect the live Codex app-server thread but may not be durably safe across the VS Code / Codex restart restoration path.
|
|
37
|
+
|
|
38
|
+
## Impact
|
|
39
|
+
|
|
40
|
+
Severity: high.
|
|
41
|
+
|
|
42
|
+
The failure mode is not just stale context. A past user instruction can be resurrected and processed as a fresh user request after restart or reconnect.
|
|
43
|
+
|
|
44
|
+
In this incident the resurrected prompt was a harmless question:
|
|
45
|
+
|
|
46
|
+
```text
|
|
47
|
+
codexのtool.dbについても、Claudeと同様にグローバルにも存在していて、読み取りロジックは完全に同様なんだっけ
|
|
48
|
+
```
|
|
49
|
+
|
|
50
|
+
But if the resurrected turn had been an operational command such as publish, install, deploy, delete, rebuild, or migration work, Codex could execute an obsolete request.
|
|
51
|
+
|
|
52
|
+
## Observed Timeline
|
|
53
|
+
|
|
54
|
+
All timestamps below are UTC from the Codex rollout JSONL.
|
|
55
|
+
|
|
56
|
+
### Original User Turn
|
|
57
|
+
|
|
58
|
+
Rollout file:
|
|
59
|
+
|
|
60
|
+
```text
|
|
61
|
+
/home/kite/.codex/sessions/2026/05/06/rollout-2026-05-06T22-17-09-019dfd6f-640e-7dd3-b163-3f9add39fde7.jsonl
|
|
62
|
+
```
|
|
63
|
+
|
|
64
|
+
The original user prompt exists at:
|
|
65
|
+
|
|
66
|
+
```text
|
|
67
|
+
line 1276 2026-05-06T14:20:35.371Z response_item role=user
|
|
68
|
+
line 1277 2026-05-06T14:20:35.371Z event_msg user_message
|
|
69
|
+
```
|
|
70
|
+
|
|
71
|
+
Prompt:
|
|
72
|
+
|
|
73
|
+
```text
|
|
74
|
+
codexのtool.dbについても、Claudeと同様にグローバルにも存在していて、読み取りロジックは完全に同様なんだっけ
|
|
75
|
+
```
|
|
76
|
+
|
|
77
|
+
### Throughline Trim Execute
|
|
78
|
+
|
|
79
|
+
The trim command was invoked at:
|
|
80
|
+
|
|
81
|
+
```text
|
|
82
|
+
line 1781 2026-05-06T14:39:43.844Z function_call
|
|
83
|
+
```
|
|
84
|
+
|
|
85
|
+
Command:
|
|
86
|
+
|
|
87
|
+
```bash
|
|
88
|
+
rtk throughline trim --execute --host codex --all
|
|
89
|
+
```
|
|
90
|
+
|
|
91
|
+
The command completed at:
|
|
92
|
+
|
|
93
|
+
```text
|
|
94
|
+
line 1790 2026-05-06T14:39:47.486Z exec_command_end
|
|
95
|
+
line 1795 2026-05-06T14:39:53.765Z function_call_output
|
|
96
|
+
```
|
|
97
|
+
|
|
98
|
+
Throughline reported:
|
|
99
|
+
|
|
100
|
+
```text
|
|
101
|
+
Status: executed
|
|
102
|
+
Reason: rollback_and_inject_sent
|
|
103
|
+
Rollback sent: yes
|
|
104
|
+
Inject sent: yes
|
|
105
|
+
Rollback candidate turns: 19
|
|
106
|
+
```
|
|
107
|
+
|
|
108
|
+
### Restart / Reconnect Symptoms
|
|
109
|
+
|
|
110
|
+
After the trim execution, the user observed Codex reconnect failures:
|
|
111
|
+
|
|
112
|
+
```text
|
|
113
|
+
Reconnecting... 2/5
|
|
114
|
+
Reconnecting... 3/5
|
|
115
|
+
Reconnecting... 4/5
|
|
116
|
+
Reconnecting... 5/5
|
|
117
|
+
stream disconnected before completion
|
|
118
|
+
```
|
|
119
|
+
|
|
120
|
+
The user then restarted VS Code.
|
|
121
|
+
|
|
122
|
+
### Duplicated User Turn
|
|
123
|
+
|
|
124
|
+
After the restart, the same prompt appeared again as if it were newly submitted:
|
|
125
|
+
|
|
126
|
+
```text
|
|
127
|
+
line 1864 2026-05-06T14:48:02.120Z response_item role=user
|
|
128
|
+
line 1865 2026-05-06T14:48:02.121Z event_msg user_message
|
|
129
|
+
```
|
|
130
|
+
|
|
131
|
+
Duplicated prompt:
|
|
132
|
+
|
|
133
|
+
```text
|
|
134
|
+
codexのtool.dbについても、Claudeと同様にグローバルにも存在していて、読み取りロジックは完全に同様なんだっけ
|
|
135
|
+
```
|
|
136
|
+
|
|
137
|
+
The user explicitly denied sending this prompt again:
|
|
138
|
+
|
|
139
|
+
```text
|
|
140
|
+
line 1883 2026-05-06T14:49:52.993Z response_item role=user
|
|
141
|
+
line 1884 2026-05-06T14:49:52.993Z event_msg user_message
|
|
142
|
+
```
|
|
143
|
+
|
|
144
|
+
User statement:
|
|
145
|
+
|
|
146
|
+
```text
|
|
147
|
+
俺はVSCを再起動しただけなんだよね。何が起きた?
|
|
148
|
+
```
|
|
149
|
+
|
|
150
|
+
## Evidence Commands Used
|
|
151
|
+
|
|
152
|
+
Duplicate prompt search:
|
|
153
|
+
|
|
154
|
+
```bash
|
|
155
|
+
rtk node -e "const fs=require('fs'); const p='/home/kite/.codex/sessions/2026/05/06/rollout-2026-05-06T22-17-09-019dfd6f-640e-7dd3-b163-3f9add39fde7.jsonl'; let i=0; for (const line of fs.readFileSync(p,'utf8').split('\n')) { i++; if (!line.trim()) continue; const row=JSON.parse(line); const payload=row.payload||{}; let text=''; let kind=''; if (row.type==='response_item' && payload.type==='message' && payload.role==='user') { kind='response_user'; text=(payload.content||[]).map(x=>x.text||x.input_text||'').join('\n'); } if (row.type==='event_msg' && payload.type==='user_message') { kind='event_user'; text=payload.message||''; } if (text.includes('codexのtool.dbについても')) console.log(JSON.stringify({line:i,timestamp:row.timestamp,kind,text:text.slice(0,160)})); }"
|
|
156
|
+
```
|
|
157
|
+
|
|
158
|
+
Output:
|
|
159
|
+
|
|
160
|
+
```json
|
|
161
|
+
{"line":1276,"timestamp":"2026-05-06T14:20:35.371Z","kind":"response_user","text":"codexのtool.dbについても、Claudeと同様にグローバルにも存在していて、読み取りロジックは完全に同様なんだっけ \n"}
|
|
162
|
+
{"line":1277,"timestamp":"2026-05-06T14:20:35.371Z","kind":"event_user","text":"codexのtool.dbについても、Claudeと同様にグローバルにも存在していて、読み取りロジックは完全に同様なんだっけ \n"}
|
|
163
|
+
{"line":1864,"timestamp":"2026-05-06T14:48:02.120Z","kind":"response_user","text":"codexのtool.dbについても、Claudeと同様にグローバルにも存在していて、読み取りロジックは完全に同様なんだっけ \n"}
|
|
164
|
+
{"line":1865,"timestamp":"2026-05-06T14:48:02.121Z","kind":"event_user","text":"codexのtool.dbについても、Claudeと同様にグローバルにも存在していて、読み取りロジックは完全に同様なんだっけ \n"}
|
|
165
|
+
{"line":1883,"timestamp":"2026-05-06T14:49:52.993Z","kind":"response_user","text":"ちょっとまってな 俺が\n\ncodexのtool.dbについても、Claudeと同様にグローバルにも存在していて、読み取りロジックは完全に同様なんだっけ \n\nを発言したことになっているんだが、\n俺はVSCを再起動しただけなんだよね。何が起きた?\n"}
|
|
166
|
+
{"line":1884,"timestamp":"2026-05-06T14:49:52.993Z","kind":"event_user","text":"ちょっとまってな 俺が\n\ncodexのtool.dbについても、Claudeと同様にグローバルにも存在していて、読み取りロジックは完全に同様なんだっけ \n\nを発言したことになっているんだが、\n俺はVSCを再起動しただけなんだよね。何が起きた?\n"}
|
|
167
|
+
```
|
|
168
|
+
|
|
169
|
+
Rollback / injection search:
|
|
170
|
+
|
|
171
|
+
```bash
|
|
172
|
+
rtk node -e "const fs=require('fs'); const p='/home/kite/.codex/sessions/2026/05/06/rollout-2026-05-06T22-17-09-019dfd6f-640e-7dd3-b163-3f9add39fde7.jsonl'; let i=0; for (const line of fs.readFileSync(p,'utf8').split('\n')) { i++; if (!line.trim()) continue; const row=JSON.parse(line); const s=JSON.stringify(row); if (s.includes('trim --execute') || s.includes('rollback_and_inject_sent') || s.includes('Rollback sent: yes')) console.log(JSON.stringify({line:i,timestamp:row.timestamp,type:row.type,payloadType:row.payload?.type,preview:s.slice(0,1000)})); }"
|
|
173
|
+
```
|
|
174
|
+
|
|
175
|
+
Relevant output:
|
|
176
|
+
|
|
177
|
+
```text
|
|
178
|
+
line 1781 2026-05-06T14:39:43.844Z trim --execute command
|
|
179
|
+
line 1790 2026-05-06T14:39:47.486Z exec_command_end, Status: executed, Rollback sent: yes, Inject sent: yes
|
|
180
|
+
line 1795 2026-05-06T14:39:53.765Z function_call_output, Status: executed, Rollback sent: yes, Inject sent: yes
|
|
181
|
+
```
|
|
182
|
+
|
|
183
|
+
Durable rollback event search:
|
|
184
|
+
|
|
185
|
+
```bash
|
|
186
|
+
rtk node -e "const fs=require('fs'); const p='/home/kite/.codex/sessions/2026/05/06/rollout-2026-05-06T22-17-09-019dfd6f-640e-7dd3-b163-3f9add39fde7.jsonl'; let i=0; for (const line of fs.readFileSync(p,'utf8').split('\n')) { i++; if (!line.trim()) continue; const row=JSON.parse(line); const payload=row.payload||{}; if ((row.type==='event_msg' && String(payload.type||'').includes('rollback')) || JSON.stringify(row).includes('thread/rollback') || JSON.stringify(row).includes('thread/inject_items')) console.log(JSON.stringify({line:i,timestamp:row.timestamp,type:row.type,payloadType:payload.type,msg:JSON.stringify(payload).slice(0,260)})); }"
|
|
187
|
+
```
|
|
188
|
+
|
|
189
|
+
Initial analysis said this did not show a durable rollout-level `thread_rolled_back` event corresponding to the app-server rollback. That was incorrect.
|
|
190
|
+
|
|
191
|
+
Follow-up audit found:
|
|
192
|
+
|
|
193
|
+
```text
|
|
194
|
+
line 1775 2026-05-06T14:39:34.452Z compacted
|
|
195
|
+
line 1778 2026-05-06T14:39:34.453Z context_compacted
|
|
196
|
+
line 1784 2026-05-06T14:39:44.844Z event_msg thread_rolled_back num_turns=19
|
|
197
|
+
```
|
|
198
|
+
|
|
199
|
+
The `compacted.replacement_history` at line 1775 contains the later-resurrected user prompt. Therefore the stronger failure hypothesis is not "rollback marker missing", but "rollback marker exists, while another restore source such as compacted replacement history or pending input can still reintroduce old user text".
|
|
200
|
+
|
|
201
|
+
## Current Hypothesis
|
|
202
|
+
|
|
203
|
+
The most likely failure path is:
|
|
204
|
+
|
|
205
|
+
```text
|
|
206
|
+
Throughline sends Codex app-server thread/rollback and thread/inject_items
|
|
207
|
+
↓
|
|
208
|
+
The live app-server thread reports success
|
|
209
|
+
↓
|
|
210
|
+
The rollout contains thread_rolled_back, but compacted.replacement_history or another restart / pending-input source still contains rollback-targeted user text
|
|
211
|
+
↓
|
|
212
|
+
VS Code restarts
|
|
213
|
+
↓
|
|
214
|
+
Codex restores from a source not covered by Throughline's current guarded execute checks
|
|
215
|
+
↓
|
|
216
|
+
A previously rolled-back user turn is restored as a fresh user message
|
|
217
|
+
```
|
|
218
|
+
|
|
219
|
+
This suggests that Codex app-server `thread/rollback` is not sufficient by itself as a durable trim primitive for VS Code restart/reconnect behavior unless the compacted / restart restore path is also verified.
|
|
220
|
+
|
|
221
|
+
## Throughline Areas To Inspect
|
|
222
|
+
|
|
223
|
+
The report does not modify Throughline. These are the areas likely involved:
|
|
224
|
+
|
|
225
|
+
```text
|
|
226
|
+
/home/kite/projects/Throughline/src/cli/trim.mjs
|
|
227
|
+
```
|
|
228
|
+
|
|
229
|
+
- `trim --execute --host codex --all`
|
|
230
|
+
- `runExecute`
|
|
231
|
+
- selection of rollout source versus DB memory source
|
|
232
|
+
|
|
233
|
+
```text
|
|
234
|
+
/home/kite/projects/Throughline/src/codex-app-server.mjs
|
|
235
|
+
```
|
|
236
|
+
|
|
237
|
+
- `runCodexTrimExecution`
|
|
238
|
+
- `thread/rollback`
|
|
239
|
+
- `thread/inject_items`
|
|
240
|
+
- post-inject read consistency check
|
|
241
|
+
- whether the check proves durable restore behavior or only live app-server state
|
|
242
|
+
|
|
243
|
+
```text
|
|
244
|
+
/home/kite/projects/Throughline/src/codex-rollout-memory.mjs
|
|
245
|
+
```
|
|
246
|
+
|
|
247
|
+
- `parseCodexRolloutFile`
|
|
248
|
+
- handling of `thread_rolled_back`
|
|
249
|
+
- assumptions about rollback events being present in rollout JSONL
|
|
250
|
+
|
|
251
|
+
## Recommended Immediate Guard
|
|
252
|
+
|
|
253
|
+
Until durable restart behavior is proven, `$throughline` should not automatically execute:
|
|
254
|
+
|
|
255
|
+
```bash
|
|
256
|
+
throughline trim --execute --host codex --all
|
|
257
|
+
```
|
|
258
|
+
|
|
259
|
+
Recommended short-term behavior:
|
|
260
|
+
|
|
261
|
+
- Keep `doctor`
|
|
262
|
+
- Keep `trim --dry-run`
|
|
263
|
+
- Keep `trim --preflight`
|
|
264
|
+
- Require explicit user action for `trim --execute`
|
|
265
|
+
- Add a warning that Codex app-server rollback may not survive VS Code restart
|
|
266
|
+
|
|
267
|
+
If automatic execution remains available, it should require an additional durable verification step:
|
|
268
|
+
|
|
269
|
+
```text
|
|
270
|
+
execute rollback/inject
|
|
271
|
+
read live thread
|
|
272
|
+
verify rollout JSONL contains durable rollback marker
|
|
273
|
+
verify compacted replacement history / restart restore sources cannot reintroduce rollback-targeted user text
|
|
274
|
+
restart/reconnect smoke or simulated restore check
|
|
275
|
+
only then report success as durable
|
|
276
|
+
```
|
|
277
|
+
|
|
278
|
+
## Suggested Regression Test Shape
|
|
279
|
+
|
|
280
|
+
A fake app-server test is not sufficient unless it models the persistence mismatch.
|
|
281
|
+
|
|
282
|
+
Recommended test:
|
|
283
|
+
|
|
284
|
+
1. Create a rollout JSONL with multiple user turns.
|
|
285
|
+
2. Simulate app-server `thread/rollback` returning success.
|
|
286
|
+
3. Do not mutate the rollout JSONL.
|
|
287
|
+
4. Run the restore / parse path used after restart.
|
|
288
|
+
5. Assert that Throughline refuses to call the trim durable, or warns that rollback is live-only.
|
|
289
|
+
|
|
290
|
+
Acceptance criteria:
|
|
291
|
+
|
|
292
|
+
- Throughline must not report a Codex trim as durable unless the restore source reflects the rollback.
|
|
293
|
+
- A rolled-back user turn must not be eligible to reappear as a fresh user request after restart.
|
|
294
|
+
|
|
295
|
+
## Open Questions
|
|
296
|
+
|
|
297
|
+
- Does Codex app-server expose a durable rollback primitive, or is `thread/rollback` live-session only?
|
|
298
|
+
- Is there a separate persisted thread store besides rollout JSONL that VS Code uses on restart?
|
|
299
|
+
- Can Throughline inject a durable marker that Codex restore respects?
|
|
300
|
+
- Should Throughline switch Codex trim from mutation-based rollback to resume-only memory rendering until durable rollback is proven?
|
|
301
|
+
|
|
302
|
+
## Bottom Line
|
|
303
|
+
|
|
304
|
+
Treat this as a blocker for automatic Codex trim execution.
|
|
305
|
+
|
|
306
|
+
The observed incident demonstrates that `trim --execute --host codex --all` can report success while a rolled-back user turn later reappears after VS Code restart. Throughline should not expose this as a safe default until durable rollback semantics are verified end to end.
|
|
@@ -0,0 +1,57 @@
|
|
|
1
|
+
[
|
|
2
|
+
{
|
|
3
|
+
"kind": "throughline_handoff",
|
|
4
|
+
"source": "throughline",
|
|
5
|
+
"trust": "local",
|
|
6
|
+
"summary": "In-flight handoff: continue the Codex projection work.",
|
|
7
|
+
"data": {
|
|
8
|
+
"throughlineHandoffSchemaVersion": 1,
|
|
9
|
+
"handoffRecordVersion": 1,
|
|
10
|
+
"sessionId": "example-session",
|
|
11
|
+
"projectPath": "/home/kite/projects/Throughline",
|
|
12
|
+
"sourceAgent": "claude",
|
|
13
|
+
"hostMode": "claude-primary",
|
|
14
|
+
"intent": "continue implementation",
|
|
15
|
+
"constraints": [
|
|
16
|
+
"preserve existing Claude Code hook, slash command, transcript, baton, and resume behavior",
|
|
17
|
+
"add Codex support as adapter/projection; do not rename Claude-facing DB fields or commands"
|
|
18
|
+
],
|
|
19
|
+
"originSessionIds": [
|
|
20
|
+
"example-origin"
|
|
21
|
+
],
|
|
22
|
+
"stats": {
|
|
23
|
+
"l1Rows": 0,
|
|
24
|
+
"l2Rows": 1,
|
|
25
|
+
"thinkingRows": 0,
|
|
26
|
+
"l3References": 1,
|
|
27
|
+
"preservedContextRows": 1
|
|
28
|
+
},
|
|
29
|
+
"memory": {
|
|
30
|
+
"inflightMemo": "Continue Phase 5 read-only sidecar smoke.",
|
|
31
|
+
"latestThinking": [],
|
|
32
|
+
"l1Summaries": [],
|
|
33
|
+
"recentBodies": [
|
|
34
|
+
{
|
|
35
|
+
"originSessionId": "example-origin",
|
|
36
|
+
"turnNumber": 1,
|
|
37
|
+
"role": "assistant",
|
|
38
|
+
"text": "Configured throughline_handoff projection and diagnostics wrapper.",
|
|
39
|
+
"createdAt": 1770000000000,
|
|
40
|
+
"time": "12:00:00"
|
|
41
|
+
}
|
|
42
|
+
]
|
|
43
|
+
},
|
|
44
|
+
"detailReferences": [
|
|
45
|
+
{
|
|
46
|
+
"type": "throughline_detail",
|
|
47
|
+
"label": "tool_input:Bash",
|
|
48
|
+
"command": "throughline detail 12:00:00",
|
|
49
|
+
"sourceId": "toolu_example",
|
|
50
|
+
"detailKind": "tool_input",
|
|
51
|
+
"originSessionId": "example-origin",
|
|
52
|
+
"turnNumber": 1
|
|
53
|
+
}
|
|
54
|
+
]
|
|
55
|
+
}
|
|
56
|
+
}
|
|
57
|
+
]
|