Skip to content

v0.40.0

Choose a tag to compare

@Kewton Kewton released this 21 Sep 14:14
· 22 commits to main since this release
9bd4369

[0.40.0] - 2026-09-21

Highlight: 検出層が画面を読めないときの逃げ道を作ったリリース。エージェントの tmux ペインへキーをそのまま届ける「直接入力」を、PC の分割ペイン(#2764〜#2766 / #2797)と、スマホの Termux 方式の画面内キーボード(#2799 / #2801 / #2824)に追加した。あわせて、分類できなかったフレームを緑の点滅(処理中)で描くのをやめ、「判別不能」(点滅しない中空のグレーの輪、ラベル「不明」)としてサイドバー・ヘッダ・Sessions・コマンドパレットに出す(#2775 / #2810 / #2822)。Command Code 1.58.0 の Plan review は検出・承認(Ctrl+A)できるようになり(#2760〜#2763 / #2793 / #2809)、codex 0.155.1 で完了後も選択リストや処理中のまま固まる誤読(#2798 / #2818)と、会話中の引用 1 行でフレームが切り落とされる問題(#2774 / #2776)を直した。スマホのチャット面では、ツール表示の切替と検索を面切替ピルの下から出し(#2821 / #2823)、ツール表示 ON で最新の返答が画面外へ押し出される問題も直した(#2820)。

Added

  • feat(mobile): スマホのチャット面で、ツール表示の一括切替(レンチ)を面切替ピルの隣に出す (#2821): スマホではチャット転写の右上にあるレンチ(#2284)と検索アイコンが面切替ピル(#2193)の下に完全に隠れていた(390x844 実測: ピル x286 y150 96×50 に対しレンチ x322・検索 x354、いずれも 28×28)。チャット面のときだけピルに 3 つ目のボタン(mobile-chat-tool-activity-toggle、44px、aria-pressed、ラベルは既存の chatTranscript.toolActivity.show / .hide、ON は PC のレンチと同じ bg-accent-500/15 text-accent-700)を区切り線つきで足し、スマホの転写は新しい hideCornerControls prop で右上のアイコン 2 つを描かない(検索バー自体は検索が開いていれば描く)。設定 commandmate:chatShowToolActivity は src/lib/chat/chat-tool-activity.ts の useChatToolActivityPreference()(useSyncExternalStore)で読むようにし、mount 時に 1 回読むだけだったのをページ全体で 1 つの値にした。ピルで切り替えると下の転写が即座に追従し、PC の分割表示では片方のレンチで全ペインが揃い、別タブの変更は storage イベントで届く。localStorage が使えないブラウザでも、画面内の切替と表示の一致は保たれる。

  • feat(mobile): スマホのターミナルに、Termux 方式の画面内キーボードによる「直接入力」を追加 (#2799): PC 専用だった #2766 の「直接入力」(検出が読めない画面の最後の出口)をスマホでも使えるようにする。「その他の操作」シートの「セッションを終了」の前に「直接入力」の行(data-testid="actions-sheet-direct-input")を足し、ターミナルタブ・ターミナル面・セッション稼働中の 3 条件がそろうときだけ押せる(満たさないときは aria-disabled と理由の短文)。開くと下部バーの composer の位置に MobileDirectInputKeyboard を描く — OS のソフトキーボードのイベントは一切読まず、Termux の Extra Keys の既定配列(11 キーを同じ位置に残し、/・-・ALT を ENTER・BS(上スワイプで DEL)・SHIFT に差し替え)の 2 段と、畳める 2 ページの文字の面(英字/数字・記号)で、DIRECT_INPUT_KEY_VALUES の 40 個と印字可能 ASCII 95 文字のすべてに届く。CTRL / SHIFT はタップでワンショット、長押しで固定。押したキーはすぐには送らず確認行にチップとして積み(続けて打った文字は 1 件の text にまとめ、同じキーの連続は ↓×3 と表示)、送信 (N) で 1 リクエストにまとめて送る(Enter は自動で付けない、上限 32 件で満杯の通知)。送信失敗時は「途中まで届いている場合がある」旨を出して列を残し、OK か列の編集まで再送信を止める(自動再送しない)。キーは pointerup で確定し、押し始めたキーがポインタを捕捉するので指が確認行へ滑っても誤爆しない。積んだ列はメモリだけに置き(localStorage 等に書かない)、インスタンス・タブの切替やセッション停止で閉じて破棄する。モード中は composer を display:none で隠して(unmount しないので下書きが残る)ナビゲーションパッド・quick keys・escape hatch を下げ、面切替ピルを押せなくし、プロンプトシートも出さない(#2755 のモード中だけの例外。タブバーのプロンプトバッジは出たまま)。useDirectInput に sendAndWait / isSending を追加(既存の send / error と PC の DirectInputBar は不変)。

  • feat(cli,api): commandmate send --model を Claude に対応 (#2771): --model は copilot / antigravity 専用だったが、Claude にも渡せるようにした。antigravity と同じ起動フラグの意味論で、この send がセッションを起動するときだけ claude --model '<値>' として効き、稼働中のセッションには 400 を返す(セッション内の /model は利用者のグローバル既定を書き換えるので使わない)。値は別名(sonnet / opus / opus[1m])か完全な ID で、CLI・route・起動直前の 3 箇所で検証する。送り先(--instance か --agent)の指定が必須。

  • feat(orchestrate): Claude 担当を opus / sonnet に振り分ける (#2770): /orchestrate の Claude 担当を難易度に応じて opus / sonnet に振り分け、サブエージェント設定を inherit に変更

  • feat(ui): PC の分割ペインに、検出に依存しない「直接入力」モードを追加 (#2766): 分割ペインの composer 上段ツールバーの右端(中断ボタンの左)に[直接入力]トグル(data-testid="direct-input-toggle" / aria-pressed)を置き、ON の間 composer の直上に DirectInputBar を描く。バーの入力欄で打ったキーは encodeKeyEvent(#2764)で DirectInputEvent に変換され、POST /api/worktrees/[id]/direct-input(#2765)を通ってそのままエージェントの tmux ペインへ届く — isSelectionListActive / isUnclassifiedActive / prompt.visible のどれにもぶら下げないので、検出が読めなかった画面(2026-09-20 の Command Code Plan review は ctrl+a でしか承認できず、ブラウザからも CLI からも打つ手が無かった)でも Ctrl+A や Esc を送れる。新設の useDirectInput は同時に飛ぶリクエストを常に 1 本に保ち、送信中に来たキーをキューへ積んで前の応答が返ってから 1 リクエスト(MAX_DIRECT_INPUT_EVENTS 件まで)にまとめるので、数十 ms 間隔の keydown が HTTP の到着順で入れ替わらない(tmux には並べ直す手掛かりが無く、届いた順がエージェントの読んだ順になる)。失敗時はキューを捨てて固定文言を出す(古いキーを後から流さない)。encodeKeyEvent が null を返すキー — Cmd+C/V/R、F キー、IME の変換中キー — は preventDefault せずブラウザに残し、IME は compositionend で確定文字列だけを 1 回送る。ペースト は改行を \r に正規化し MAX_DIRECT_INPUT_TEXT_LENGTH ごとに分割。worktreeId / cliToolId / インスタンスが変わったとき、およびセッションが落ちたときはモードを閉じる(別のペインへ打ち込み続けない)。トグルは横スクロールしない右端グループに置くので、1 / 2 / 3 分割・2x2 グリッドのどのペインでも丸ごと描かれ(#2797)、composer 行が 520px 未満ではキーボードアイコンのみ(名前は aria-label)、520px 以上でラベル付きになる。対象は PC の分割ペインのみで、スマホ・Sessions タイル・Auto-Yes の挙動は不変。

  • feat(api,tmux): 検出に依存しない直接入力 API を追加 (#2765): POST /api/worktrees/[id]/direct-input を追加。名前付きキー(Enter / Up / C-a …)と文字の列を、検出層にもツール別のキー語彙にも問い合わせずにエージェントの tmux ペインへ順番どおりに届ける。文字は send-keys -H で送る(-l は末尾の ; を落とすため)。route は tmux を直接 import せず、CLITool gateway の sendDirectInput を通る。

  • feat(types): 直接入力の語彙と keydown 変換を追加 (#2764): 検出層に依存せずエージェントのペインへキーを送る「直接入力」のための、値だけのモジュール src/types/direct-input.ts を追加。送れる名前付きキー 14 個と C-a〜C-z、DirectInputEvent(key / text)、型ガード、KeyboardEvent 相当から送信イベントへの純関数 encodeKeyEvent を持つ。配線は後続 Issue。

  • feat(ui): Command Code の Plan review に「プランを承認 (Ctrl+A)」ボタンを追加 (#2762): Plan review 画面(Approve ctrl+a / Cancel esc)はチャット面から Esc(取り消し)しか送れず、承認する手段が無かった。selection list のカードに、フレームが Plan review のときだけ承認ボタンを出し、C-a を special-keys へ送る。

  • feat(detection,prompt,ui): Command Code の複数選択 AskUserQuestion を GUI から回答できるようにする (#2755): チェックボックス型の質問(1. [ ] … / Submit)を検出・型・UI・送信・Auto-Yes 拒否の一級概念にし、GUI から複数選択して送信できるようにした。

Changed

  • chore(detection): CODEX_DIALOG_RULES_VERIFIED_AGAINST を 0.155.1 / 2026-09-21 へ進める (#2819): #2808 が codex 0.155.1 でダイアログ 5 画面(コマンド実行の承認・/model・/experimental・/keymap・trust)を採取し、すべて waiting と読めて選択行も規則が前提にする 1 スパンの形だったため、規則群のスタンプと docblock を更新した。あわせて CODEX_DIALOG_FOOTER_PATTERN の docblock のフッタ表に 0.155.1 の /experimental の文言(for next conversation が消えた)を追記した。検出器全体のスタンプ CODEX_VERIFIED_AGAINST と検出規則は変えていない。

  • test(detection): フッタ判定の未測だった claude 2.1.278 の task panel を実キャプチャで置き換える (#2811): 隔離 tmux(-L footer-probe-2、200x1000)で claude 2.1.278(Haiku 4.5、CLAUDE_CODE_ENABLE_TODO_TOOLS=1)の Bash 確認と AskUserQuestion の picker を task panel つきで採取し、tests/fixtures/tui-frame-footer-2776/ に追加した。フッタは L24 / L32(1001 行中)の行頭にあり、ペイン最下部(L997–L1000)の task panel 4 行は従来どおり切り落とされる(#2776 の行頭アンカーを支持。判定条件は変えていない)。agy 1.2.7 の通常画面は private HOME で起動すると Google OAuth の認証を求められて進めず、未測のまま理由を docs/design/tui-frame-footer-scan-2776.md に記録した。

  • test(detection): codex 0.155.1 のダイアログ 5 画面を隔離環境で実測し、#2798 の行規則で waiting に読めることを固定 (#2808): 承認・/model・/experimental・/keymap・trust の 5 画面を私設 tmux(200x1000)で採取し tests/fixtures/codex-dialogs-0155/ に置いた。選択行はどれもグリフとラベルが同じ SGR の 1 スパンで 0.146.0〜0.153.2 と同じ形、5 画面とも waiting、アイドルの入力欄は ready。同じ probe で採った「承認を断った後のアイドル」は、ステータスバーのパスの後ろにスレッド名が付くと CODEX_STATUS_BAR_PATTERN が一致せず、断ったコマンドの • Ran 行を拾って running と読まれるため、CODEX_VERIFIED_AGAINST は 0.148.0 のまま据え置いた(誤読は直さずテストで固定)。readCodexGlyphRowKind の規則を説明する docstring / README の「着色グリフなら選択肢」という旧い記述を #2798 以降の規則に合わせた。検出規則は変えていない。

  • docs(orchestrate): 「設計」と「転記」の線引きを明示し、原因特定済みバグの Phase 2.5 スキップを規定 (#2784): 1-2b の難易度判定で「設計」の行に「ワーカーが…設計して書く」と主語を明示し、本文にテスト全文がある場合は転記であって設計ではないため除外する旨と実測根拠を追記。あわせて Phase 2.5 において本文に原因(file:line)と対策が既にあるバグの委譲スキップ条件を明文化。

  • chore(detection): COMMAND_CODE_VERIFIED_AGAINST を 1.54.1 / 2026-09-20 へ進める (#2773): #2754 が据え置いた条件(規則が 1.54.1 に答えられていない)が #2753 / #2755 で解消し、26 フレームすべてが正しい判定になった(偽完了 6 枚 → 0 枚)ため、スタンプと docblock の経緯を更新した。検出規則は変えていない。

  • chore(detection): Command Code 1.58.0 の Plan review 画面を隔離環境で実測しフィクスチャ化する (#2763): 承認キー(ctrl+a はコメント 0 件なら即承認、1 件以上だとラジオの確認が挟まる)・矢印の行カーソル(背景色のみでグリフ無し、plain では不可視)・Enter(本文では安全だがアクション一覧にフォーカスが移ると承認を実行する)・ペインを消してから描かれること・1000 行を超える plan のスクロールとフッタ固定を 1 キーずつ採取し、匿名化した 24 枚の plain フィクスチャと現行検出器の verdict 表を tests/fixtures/command-code-plan-review-2763/ にまとめた(プロダクトコードの変更は 0 行)。

  • chore(detection): Command Code 1.54.1 の AskUserQuestion 画面を隔離環境で実測しフィクスチャ化する (#2754): 回答済みタブ・複数選択チェックボックス・Submit行カーソル・自由文入力の実際の描画とキー意味論を隔離tmuxで採取し、tests/fixtures/command-code-askuserquestion-2754/ と設計メモにまとめた。

Fixed

  • fix(mobile): 直接入力キーボードの BS 上スワイプ(DEL)操作および 360x640 画面での端末表示高さを修正 (#2824): キーボタンのクラスを touch-manipulation から touch-none に変更し、スワイプや長押し時の指の動きがブラウザのスクロールとして判定され pointercancel になる不具合を修正。また直接入力キーボード表示中は VerificationStatusChip と BranchMismatchAlert を非表示にして、360x640 画面で端末領域の高さ 120px 以上(132px)を確保した。

  • fix(mobile): スマホのチャット面で検索できず、検索バーの右端が面切替ピルに隠れる問題を修正 (#2823): 「その他の操作」シートの「ターミナル内を検索」は terminal-search-open を投げるだけで、これを聞く TerminalDisplay はチャット面では mount されないため、チャット面では押しても何も起きなかった(転写の検索アイコンは #2821 でスマホでは描かなくなった)。シートの検索の行は、ターミナルタブがチャット面のときだけ「この会話を検索」(既存の chatTranscript.openSearch)になり、新しい window イベント chat-search-open を投げる。これに応えるのは openSearchOnWindowEvent を渡したスマホのチャット転写だけで、PC の分割ペインの転写は反応しない。開くたびに入力欄へフォーカスを戻す(既に開いているときも、シートのフォーカストラップが閉じる際に戻すフォーカスに負けない)。あわせて、ターミナルとチャットの検索バーを top-2 から top-16 へ下げ、面切替ピル(高さ 50px、下端は表示領域の上端から 58px。セッション行の有無によらない)の 6px 下に出す(TerminalDisplay / ChatTranscript の新しい省略可能 prop searchBarTopClassName、既定は top-2 のままで PC は不変)。390x844 実測で、検索バー x60〜382 y150〜196 の右端(次へ・閉じる)がピル x286〜382 y150〜200 の下にあった。

  • fix(ui): サイドバーのセッション一覧とリポジトリタブで判別不能のインスタンスを「不明」で描画 (#2822): サイドバーのセッション一覧(SessionListItem)およびリポジトリタブ(RepositoryTab / 折りたたみ一覧)で、検出層が分類できなかったインスタンス(unclassifiedInstanceIds)が緑の「準備完了」で描画されていた問題を修正。SessionRow に unclassified を追加して buildSessionRows で ready かつ unclassifiedInstanceIds に含まれる行に伝播させ、リポジトリ単位の判定 isGroupUnclassified を追加して resolveUnclassifiedDot / UNCLASSIFIED_STATUS_DOT_CLASS / UNCLASSIFIED_STATUS_LABEL_KEY により点滅しない中空の輪+「不明」として描画するようにした。

  • fix(ui): チャット面でツール表示(レンチ)が ON のとき、最新の返答が画面外に押し出される問題を修正 (#2820): 転写の着地点を「最後の行の下端」から「最新の返答行の頭」に変えた。返答行は本文 → Thinking → Tool calls の順に描かれるため、レンチ ON で行が表示領域の数倍になると(実測 1600x1000 で 287px → 2,508px、表示領域 728px)、下端に着地した転写では返答本文が約 2,500px 上の画面外にあった。着地点は ChatTranscript.tsx の resolveChatLandingTarget が決める: 末尾から承認行と screen scrape 行を飛ばし、最初に当たった行が assistant の返答ならその頭(scrollToIndex(index, { align: 'start' }))、ユーザー行などなら従来どおり最後の行の下端。返答の頭から末尾までが 1 画面に収まるときは virtualizer の clamp で自然に下端に着くので、短い返答の位置は変わらない。生成中(live tail が出ている間)は従来どおり下端に追従し、ターンが終わった時点で返答の頭へ移る。着地し直す契機に「live tail の有無の変化」と「レンチの切り替え」を加え、返答の頭で止めている状態も追従中として扱う(jump FAB は「先頭へ」のまま、読者が 80px を超えて離れたら追従をやめる)。ChatSurface 自身の scrollTop = scrollHeight が同じ commit で狙いを上書きする場合に備え、アンカーの最初のフレームで位置がずれていれば狙い直す。jump FAB・End キー・親に渡す scrollToLatest も同じ着地点へ向かう。

  • fix(detection): codex 0.154+ のスレッド名つきステータスバーを境界と認めて、コマンドを実行したターンの後のアイドルを running と誤読しない (#2818): codex はスレッドに名前が付くとバーのパスの後ろに · <スレッド名>(Plan mode では右寄せのバッジ)を描くが、境界の CODEX_STATUS_BAR_PATTERN はパスが行末にあることを要求していたため境界が見つからず、分岐 D が末尾 15 行に残った • Ran … を拾ってアイドルを running と読んでいた。findCodexFooterBoundary が新設の CODEX_TRAILED_STATUS_BAR_PATTERN も受け付けるようにし(CODEX_STATUS_BAR_PATTERN 自体は変えていない)、スレッド名つきのバーをスレッド名の無いバーと同じ窓で読む。隔離 tmux(-L codex-bar-probe、200x1000)で codex 0.155.1 の sleep 30 実行中 2 枚と完了後のアイドル 1 枚を採取して tests/fixtures/codex-thread-title-probe/ に置き、実行中は running、アイドルは ready と読めることを確かめた。fixture の全走査(504 フレーム)で判定が変わったのは誤読していたアイドル 2 枚だけ。全画面が正しく読めたので CODEX_VERIFIED_AGAINST を 0.155.1(2026-09-21)へ進めた。

  • fix(ui,api): 「判別不能」表示を Sessions 一覧・コマンドパレット・スマホのヘッダにも適用し、PC 分割ペインの「Queued (session busy)」と停滞判定の食い違いを直す (#2810): #2775 で未適用だった 3 箇所で、検出層が分類できなかったエージェント(sessionStatusByCli.<tool>.isUnclassified)を「判別不能」(点滅しない中空のグレーの輪、ラベル「不明」)で描く。Sessions 一覧では「+N」の待機グループに畳まず独立したチップにし、コマンドパレットの優先順は waiting > running > 判別不能 > ready。PC の分割ペインは、タイトルバーが「不明」のとき送信しても「Queued (session busy)」を出さない(スマホと同じ答え)。/api/worktrees?include=review は、判別不能かつ停滞中のセッションを再び「停滞を確認」(reviewStatus: 'stalled')と返す。一覧のポーリング間隔とサイドバーの並び順は ready 扱いのまま据え置く。根拠のある running(thinking_indicator 等)の表示は変わらない。

  • fix(ui): ターミナル表示側の矢印パッドも Command Code の Plan review では Enter を出さない (#2809): #2793 でチャット面のカードから外した Enter を、PC 分割ペインのフッタとスマホのドックの NavigationButtons からも外した。アクション一覧(❯ Approve)にフォーカスがあると Enter が plan を実行するため。判定はどちらも readSelectionListShape(...).offersPlanApprove。スマホは useWorktreeDetailController の current-output 取得で realtimeSnippet || fullOutput から boolean だけを計算して公開する(フレーム本体は mirror しない)。承認確認ラジオや codex / claude の承認ダイアログでは従来どおり Enter が出る。

  • fix(types): 直接入力で日本語 IME を確定する Enter がペインへ送られうる経路を塞ぐ (#2801): WebKit 310826@main より前の Safari(同世代の iOS / iPadOS Safari を含む)は、変換を確定する Enter の keydown を compositionend の後に isComposing: false で送る。encodeKeyEvent は isComposing しか見ていなかったため、確定文字列の直後にこの Enter を { type: 'key', key: 'Enter' } として送り、エージェントの composer を送信したりダイアログのハイライト中の選択肢を確定したりしうる状態だった(実機での再現は未確認)。KeyEventLike に keyCode? を足し、MessageInput と同じく IME 処理中のキーを示す keyCode === 229 を null(preventDefault しない・送らない)にした。229 は物理キーに割り当たらない値なので、通常のキー入力や、確定後にユーザーが改めて押す Enter(keyCode: 13)は従来どおり送られる。

  • fix(detection): codex 0.155.1 のアイドル入力欄を選択リストと誤判定し、完了後もチャット面が選択リスト表示のまま固まる問題を修正 (#2798): 0.155.1 が入力欄の › を太字+truecolor で描くようになり、readCodexGlyphRowKind() が色だけで option と読んでいたため、ターン完了後も waiting / codex_selection_list(wait は exit 10、Pick パッドに回答本文の番号付き段落)になっていた。dim のラベル(入力欄のプレースホルダ)を入力欄の肯定的な証拠とし、色は「ラベルがグリフと同じ色で描かれている(1 スパンの強調)」ときだけ選択肢の根拠にするよう改め、ready / input_prompt に戻した。#2310 の番号なしメニュー(/experimental / /keymap)と trust ダイアログは従来どおり waiting、既存の codex fixture 40 件の判定は不変。

  • fix(ui): 2 分割ペインと 2x2 グリッドで[直接入力]トグルが出ない (#2797): トグルを composer のメタ行から上段ツールバーの右端グループ(composer-toolbar-end、中断ボタンの左)へ移した。右端グループは縮まず横スクロールもしないので、1・2・3 分割と 2x2 グリッドのどのペインでもトグルが丸ごと描かれる。メタ行では 2 分割・グリッド(行 431px)でヒントと Auto-Yes に場所を取られて描かれず、3 分割でも横スクロールする Auto-Yes 帯の末尾に置かれていたため狭いペインでは見切れていた(実測: 行 174px で Auto-Yes OFF でも 78px 中 10px、ON で 0px)。トグルは行幅 520px 未満(2 分割・グリッド・3 分割)ではキーボードアイコンのみ(24px、名前は aria-label / title)、520px 以上(1 分割)でラベル付き。メタ行は #2598 の予算(ヒント+Auto-Yes)に戻り、2 分割でもヒントは出たまま。2 分割・グリッドでは mode コントロール(chip・注意書き)を 1px も削らない。3 分割の最も狭い 2 ペイン(行 174px の claude・271px の codex)だけは元から余白が 0 で、mode コントロールが 28px 譲る(#2597 の設計どおり chip/注意書きが省略表示になり、mode ボタンは欠けない)。MessageInput に directInputSlot を追加(未指定の呼び出し元は描画不変)。実測は tests/e2e/composer-two-row-2598.spec.ts の MEASURE-2797。

  • fix(detection,ui): Command Code の Plan review でアクション一覧にフォーカスした画面の偽完了と、承認確認ラジオの未分類を直し、矢印パッドの Enter を隠す (#2793): COMMAND_CODE_PLAN_REVIEW_FOOTER が ❯ Approve ctrl+a / ❯ Cancel esc の行頭カーソルを許すようにし、wait が exit 0 を返していた 2 枚を waiting / command_code_plan_review に戻した。コメント付きの ctrl+a で挟まるラジオ(Approve (•) with N comments as notes … / ←/→ choose · enter confirm · esc back)を isCommandCodePlanApproveChoice() で同じ verdict に揃えた。offersPlanApprove のときチャット面の NavigationButtons から Enter(ボタンとキーボード)を外し、承認は「プランを承認 (Ctrl+A)」ボタンに一本化した。#2763 の 24 枚を全件走査するテストで残り 20 枚の verdict が変わらないことを pin した。

  • fix(orchestrate): ワーカーにテスト全体を実行させる条件を狭め、受入基準の記述による誤実行を防ぐ (#2781): /orchestrate の goal 雛形および差し替え条件を改訂し、Issue の受入基準に npm run test:unit とあることだけではテスト全体を実行させない旨を明記。verify とワーカー直接実行の mutex 非対称による偽のテスト失敗(ティアダウン race)を防ぐとともに、3-4 の帰属判定手順および issue-create テンプレートの注意書きを追加。

  • fix(orchestrate): 冷間起動の失敗(send が exit 99)で約 2 分待つ前に capture で画面を見る (#2780): 新規 worktree でほぼ必ず出る信頼ダイアログやプロンプト準備完了時の無駄な 2 分待ちを避けるため、待つ前に capture で画面を見て即時再送または待機に分岐するよう改訂。

  • fix(detection): 会話本文がフッタ文言を引用しただけでフレームが切り落とされるのを止める (#2776): normalizeTuiFrameForDetection は Esc to cancel · Tab to amend / Enter to select … navigate を含む行を Claude のフッタと見なしてその上下を捨てるが、位置を見ていなかったため、依頼文や返答の中の引用 1 行でも発火していた(2774 では 1002 行中 963 行)。隔離 tmux(200x1000)で claude 2.1.278 / codex 0.155.1 / command-code 1.58.0 を採取し、本物のフッタは全行が行頭(前は空白と SGR だけ)、引用は全行が前に可視文字を持つことを確かめて、両パターンに行頭アンカーを足した。画面下部への限定と捨てる量の上限は、本物のフッタが 1000 行ペインの上端側に描かれ(L25–L108)、非空行で数えた距離が引用と重なるため採らなかった(docs/design/tui-frame-footer-scan-2776.md)。

  • fix(ui,session): 検出層が分類できなかったフレームを「処理中」(緑の点滅)として表示しない (#2775): 判定チェーンの床(default / unknown_frame / no_recent_output、isUnclassifiedFrame())に落ちた running を worktree 一覧 API が isProcessing: true に写していた問題を修正。活動フラグは立てずに isUnclassified: true を publish し、サイドバー・PC ヘッダ(ワークツリー点/エージェントピル)・スマホのエージェントタブ・分割ペインのタイトルバー・Sessions タイル・Review の点は「判別不能」(点滅しない中空のグレーの輪、ラベル「不明」)で描く。commandmate ls / peers も running ではなく ready を表示する(REASON 列は default (no evidence) のまま)。根拠のある running(thinking_indicator 等)の表示は変わらない。

  • fix(detection): 会話本文が picker フッタを引用すると codex が永久に「処理中」になる (#2774): normalizeTuiFrameForDetection は Enter to select … navigate を含む行を見つけるとその行より下を捨てるが、下に新しい対話(CLAUDE_LOWER_INTERACTIVE_ANCHOR)があれば捨てない。このアンカーの文字クラスが [>❯] だけで codex の composer ›(U+203A) を含まなかったため、依頼文に引用された 1 行でエージェントの出力全部と composer が消え、15 行窓に promptPattern が当たらず running / default / evidence=none に張り付いていた(2026-09-20 の実例は 1002 行が 38 行に切れた)。文字クラスに › を 1 文字足して直す。他の 6 ツールの composer は > か ❯ で従来から対象。

  • fix(tmux): send-keys が本文末尾の ; を落とす問題を修正 (#2769): tmux は send-keys の引数の末尾の ; をコマンド区切りとして食うため(-l -- でも同じ)、; で終わる 512 バイト以下のメッセージが末尾の ; 抜きでエージェントに届き、literal でない経路(copilot の一部スラッシュコマンド、transport の fallback)では unknown command: C-m で送信ごと失敗していた。末尾の ; の直前にバックスラッシュを 1 本足してから argv に載せる。

  • fix(session): 上端寄せのペインで realtimeSnippet が空行だけになる問題を修正 (#2768): ペインは 200x1000 固定で、inline で描くツール(codex / antigravity / Command Code など)は上端から描くため、キャンバスを埋めるまで capture の末尾 100 行がすべて空行になり、realtimeSnippet から何も読めなかった(上流障害バナーの検出も効かない)。末尾 100 行がすべて空行のときだけ、最後の内容行で終わる 100 行を返す。末尾に内容があるフレームの結果は変わらない。

  • fix(tmux): ブラウザ端末の入力が tmux コマンドとして実行される問題を修正 (#2767): TmuxControlClient.sendInput() が入力を control mode の stdin へそのまま書いていたため、/worktrees/[id]/terminal で打った行が tmux コマンドとして解釈され(kill-server で全セッションが落ちる)、ペインには届いていなかった。入力を send-keys -H(16 進)に包んで送る。control mode は既定で無効のため、既定構成では発火しない。

  • fix(detection): Command Code の Plan review 画面を waiting として検出する (#2761): 1.58.0 の Plan review(フッタ Approve ctrl+a / Cancel esc)が running / default(unclassified)として publish され、チャット面は「thinking…」のまま 18 個のボタンを出し、plan 本文が (y/n) で終わると Auto-Yes が y をコメントとして打ち込みうる状態だった。beforePrompt で読み取り waiting / command_code_plan_review(selection list の一員)として publish する。番号ボタンは出さない。

  • fix(tmux,cli-tools): Command Code に Ctrl+A(C-a)を送れるようにする (#2760): Plan review 画面(Approve ctrl+a / Cancel esc)は ctrl+a でしか承認できないが、ALLOWED_SPECIAL_KEYS にも command-code の navigationKeys() にも C-a が無く、special-keys API が 400 を返していた。transport に C-a を足し、command-code 専用の語彙 COMMAND_CODE_NAVIGATION_KEY_VALUES で宣言する。claude ほか他ツールの語彙は変えない。

  • fix(detection): Command Code 1.54.1 の回答済みタブ(✔)を AskUserQuestion のタブ行として認識 (#2753): isCommandCodeQuestionTabRow() のタブ行語彙に U+2714 を追加し、1.54.1 が複数質問の回答済みタブに描く ✔ で専用リーダが none を返していた問題を修正。複数選択の質問が単一選択として誤読され回答可能な payload が publish される事象が解消し、#2521 の矢印カード(人が操作する画面)に戻る。