Skip to content

feat(u3-question-route-observability): QUESTION_ANSWERED に解決経路の観測属性を追加する - #2487

Merged
j5ik2o merged 6 commits into
mainfrom
bolt-2378-u3-question-route
Aug 8, 2026
Merged

feat(u3-question-route-observability): QUESTION_ANSWERED に解決経路の観測属性を追加する#2487
j5ik2o merged 6 commits into
mainfrom
bolt-2378-u3-question-route

Conversation

@j5ik2o

@j5ik2o j5ik2o commented Aug 8, 2026

Copy link
Copy Markdown
Member

概要

Intent 260807-autonomy-reachability の unit u3-question-route-observabilityQUESTION_ANSWERED 監査イベントへ質問の解決経路(route)の観測属性を追加する。

FR 要約

  • FR-3a: Route は optional --decision-id からの導出属性である。呼び出し元が auto-decision id を渡した場合のみ auto 系 route が導出され、渡さない場合は従来どおりの human route として記録される。既存呼び出し元への必須フラグ追加はない。
  • FR-3b: 新規の拒否経路は追加しない。唯一の新規検査は --decision-idauto-decision- 形式検査であり、malformed id は exit 1 で loud に停止し QUESTION_ANSWERED を emit しない(t486 で落ちる実証を固定)。迂回述語(route=human × autonomy=semi/full の組)は観測専用で、検出しても停止しない。
  • FR-3c: 事後読取(observation-only sweep)では、decode 不能な INTENT_AUTONOMY_TRANSACTION_COMMITTED 行があっても読取全体を fail させず最後の既知 mode を維持する — 迂回質問の過剰検出側に倒す(t486/t487 でピン)。この observation-only catch は no-silent-drop 台帳へ grant イベント(01KZF9NRBGKJZKY9TGJAJYQ45G、NSD001、enhancement(engine): Intent autonomy full でも人間裁定が残る構造要因を計測した — 人間ターンの74%はモード設定前、presence guard 拒否231件/63 intents #2378)として登録し、approval census を 213 → 214 へ再束縛した。
  • 後方互換: u3 以前に記録された QUESTION_ANSWERED 行の route は unknown として読まれる。

検証結果(いずれも exit code を個別捕捉)

検証 exit
bun run typecheck 0
bun run lint 0
bun test(t487 / t486 / no-silent-drop-gate / no-silent-drop-repository-adoption / t413 / t-coverage-mechanism-ratchet / event-registry-drift、--timeout=60000) 0(121 pass / 0 fail / 918 expect)
bun tests/no-silent-drop-gate.ts approve-evidence 0
bun tests/gen-coverage-registry.ts --check 0
bun run build 後の追跡ファイル不変(git status --short = 台帳変更のみ) 確認済み

census 実測: counts = { C_pre: 214, B_pre: 214, B0: 214 } / censusDigest = f89c1bcd9e3999c8d801a110df18d2b1b7e66286c7ed871dca5e0f6631b8c175

レビュー

  • §12a functional-design レビュー READY ×2 iteration
  • 実装の独立レビュー READY

Refs #2378


Note

Low Risk
Observability-only audit attributes and read-side predicates; existing answer flows unchanged unless callers pass --decision-id. The new malformed-id check is narrow and loud-fails without emitting.

Overview
Adds u3 question-route observability so QUESTION_ANSWERED rows record how an answer was resolved: Resolution Route (human vs ladder) and optional Decision Id, derived from whether amadeus-log answer receives a valid auto-decision-* --decision-id (no new required flags for existing callers).

amadeus-log gains route derivation (resolveQuestionRoute), an audit sweep (questionAnswerRouteRows / findBypassedQuestionAnswers) that flags direct human answers under semi/full autonomy, and treats pre-u3 rows without route as unknown. Malformed --decision-id is the only new refusal path. The observation-only sweep keeps the last known autonomy mode when an INTENT_AUTONOMY_TRANSACTION_COMMITTED row cannot be decoded (grandfathered in no-silent-drop).

Docs/registry (audit-format.md, event-registry.ts), t486/t487 tests, coverage ratchet, and NSD census 213 → 214 are updated accordingly.

Reviewed by Cursor Bugbot for commit 5599e20. Configure here.

Summary by CodeRabbit

  • 新機能
    • 質問回答の監査情報に、解決経路(人間回答/自律ラダー)と決定IDを記録できるようになりました。
    • 自律モード中の直接的な人間回答を検出し、監査結果から確認できるようになりました。
  • 改善
    • 不正な決定IDは処理前に拒否され、監査イベントが誤って作成されないようになりました。
    • 既存の監査記録や一部の判読できない記録も、適切に処理できるようになりました。
  • テスト
    • 回答経路の記録、検証、バイパス検出に関するテストを追加しました。

j5ik2o added 2 commits August 8, 2026 09:30
… route on QUESTION_ANSWERED

Add a derived Resolution Route attribute (ladder when --decision-id is
passed, human otherwise) plus an optional Decision Id to the
QUESTION_ANSWERED emit point in amadeus-log.ts, so decide-question ladder
answers and direct human answers are machine-discriminable in the audit
shard (FR-3a, #2378). Export questionAnswerRouteRows /
findBypassedQuestionAnswers, an after-the-fact sweep that derives the
Intent autonomy mode from INTENT_AUTONOMY_TRANSACTION_COMMITTED rows and
flags human answers recorded under semi/full mode (FR-3b). Observation
only: the sole new refusal is the auto-decision- shape check on an
explicitly passed --decision-id (FR-3c); pre-u3 rows read as route
unknown and existing checkpoint guards are pinned unchanged.

Tests: t487 (unit, pure derivation + predicate with a real semi-mode
transaction fixture and a falling-proof route rewrite) and t486
(integration, both routes end to end via the exported main seam, loud
malformed-id refusal, open-gate guard contrast, shard-level detection
with fixture-rewrite falling proof).
@coderabbitai

coderabbitai Bot commented Aug 8, 2026

Copy link
Copy Markdown

Review Change Stack

📝 Walkthrough

Walkthrough

QUESTION_ANSWERED に解決ルートと決定IDを追加しました。CLI は決定IDを検証してイベントへ記録します。監査ログ解析は自律モード中の人間回答を検出します。単体テスト、統合テスト、NSD001証跡を更新しました。

Changes

質問回答ルートの観測

Layer / File(s) Summary
監査契約とイベント出力
packages/framework/core/knowledge/.../audit-format.md, packages/framework/core/otel/event-registry.ts, packages/framework/core/tools/amadeus-log.ts
QUESTION_ANSWERED の任意属性に Resolution RouteDecision Id を追加しました。回答イベントは人間ルートまたはラダールートを記録します。
ルート導出とCLI処理
packages/framework/core/tools/amadeus-log.ts
監査ログから自律モードと回答ルートを復元します。復号不能なトランザクションでは直前のモードを維持します。不正な --decision-id を拒否します。
ルート検証と観測テスト
tests/unit/t489-question-route-derivation.test.ts, tests/integration/t488-question-route-observability.integration.test.ts
回答ルート、決定ID、承認ゲート、旧形式ログ、semi/full モード中の人間回答検出を検証します。
監査証跡とカバレッジ更新
tests/.coverage-registry.json, tests/integration/t-coverage-mechanism-ratchet.test.ts, tests/integration/t413-no-silent-drop-ci-adoption.test.ts, tests/no-silent-drop/*
新しい統合テストをカバレッジへ登録します。NSD001 の証跡と承認済み検出件数を更新します。

Estimated code review effort: 4 (Complex) | ~45 minutes

Possibly related PRs

🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 41.18% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (4 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed タイトルは、QUESTION_ANSWERED 監査イベントへの解決経路の観測属性追加という主変更を具体的かつ簡潔に示しています。
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.

Comment @coderabbitai help to get the list of available commands.

…ler onto its guarded call

error() exits the process, so the malformed --decision-id arm is only
reachable from a spawned run and the patch census counted it as an
uncovered added line. Sharing the line with the call it guards keeps the
behaviour identical while the executed assignment carries the record.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 2

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@packages/framework/core/knowledge/amadeus-shared/audit-format.md`:
- Line 150: QUESTION_ANSWERED のオプション属性一覧に、event-registry.ts の許可内容と一致する Presence
Reservation Id を追加してください。既存の属性および amadeus-log.ts answer の記載は変更しないでください。

In `@tests/unit/t487-question-route-derivation.test.ts`:
- Around line 103-159: テストに、正常な semi または full の autonomy 行の後へ復号不能な Transaction
行を追加するケースを補ってください。questionAnswerRouteRows では復号失敗後も直前の autonomyMode
が保持されることを検証し、findBypassedQuestionAnswers ではその後の human route が保持された mode
に基づいて期待どおり検出されることを確認してください。
🪄 Autofix

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: ASSERTIVE

Plan: Pro Plus

Run ID: 7d70f4ab-3432-452e-9b1c-44f9727891c9

📥 Commits

Reviewing files that changed from the base of the PR and between 51b0a95 and e4676dc.

📒 Files selected for processing (10)
  • packages/framework/core/knowledge/amadeus-shared/audit-format.md
  • packages/framework/core/otel/event-registry.ts
  • packages/framework/core/tools/amadeus-log.ts
  • tests/.coverage-registry.json
  • tests/integration/t-coverage-mechanism-ratchet.test.ts
  • tests/integration/t413-no-silent-drop-ci-adoption.test.ts
  • tests/integration/t486-question-route-observability.integration.test.ts
  • tests/no-silent-drop/approval.json
  • tests/no-silent-drop/events/01KZF9NRBGKJZKY9TGJAJYQ45G.json
  • tests/unit/t487-question-route-derivation.test.ts

Comment thread packages/framework/core/knowledge/amadeus-shared/audit-format.md
Comment thread tests/unit/t487-question-route-derivation.test.ts Outdated
j5ik2o added 2 commits August 8, 2026 12:18
…ion row and full mode

Review follow-up. The sweep's catch — an undecodable transaction keeps
the last readable mode — and the predicate's full-mode arm had no test;
both now stand on a real transaction minted through the coordinator.
u1 landed the sibling autonomy waiver, so the shared ledgers take the
union of both: the approval census carries 215 entries (213 base plus one
grant from each unit), the mechanism ratchet lists all four new spawner
tests, and t413's pin follows the census.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (2)
packages/framework/core/knowledge/amadeus-shared/audit-format.md (1)

281-281: 📐 Maintainability & Code Quality | 🟡 Minor | ⚡ Quick win

イベント数の見出しを 6 に更新してください。

INTENT_AUTONOMY_HUMAN_REQUIRED の追加後、この表は6件です。見出しは 5 events のままです。監査イベント一覧の件数を実際の行数と一致させてください。

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/framework/core/knowledge/amadeus-shared/audit-format.md` at line
281, 監査イベント一覧の見出しを `5 events` から `6 events`
に更新し、`INTENT_AUTONOMY_HUMAN_REQUIRED` を含む表の行数と一致させてください。
tests/.coverage-registry.json (1)

331-337: 🗄️ Data Integrity & Integration | 🟡 Minor | ⚡ Quick win

監査ユニットのカバレッジ登録を更新してください。

  • INTENT_AUTONOMY_HUMAN_REQUIREDt482-autonomy-refusal-event.integration.test.tscli)を追加し、statuscovered にする。
  • QUESTION_ANSWEREDt486-question-route-observability.integration.test.tscli)を追加し、statuscovered にする。
  • counts.coveredByClass.audit を 44 から 46 に更新する。
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@tests/.coverage-registry.json` around lines 331 - 337, Update the audit
coverage registry entries for INTENT_AUTONOMY_HUMAN_REQUIRED and
QUESTION_ANSWERED by adding their specified CLI integration tests to coveredBy
and changing each status to covered; then update counts.coveredByClass.audit
from 44 to 46.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Outside diff comments:
In `@packages/framework/core/knowledge/amadeus-shared/audit-format.md`:
- Line 281: 監査イベント一覧の見出しを `5 events` から `6 events`
に更新し、`INTENT_AUTONOMY_HUMAN_REQUIRED` を含む表の行数と一致させてください。

In `@tests/.coverage-registry.json`:
- Around line 331-337: Update the audit coverage registry entries for
INTENT_AUTONOMY_HUMAN_REQUIRED and QUESTION_ANSWERED by adding their specified
CLI integration tests to coveredBy and changing each status to covered; then
update counts.coveredByClass.audit from 44 to 46.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: ASSERTIVE

Plan: Pro Plus

Run ID: a83ecf2b-d190-41b0-b570-597897092eb5

📥 Commits

Reviewing files that changed from the base of the PR and between e4676dc and 4ad0549.

📒 Files selected for processing (7)
  • packages/framework/core/knowledge/amadeus-shared/audit-format.md
  • packages/framework/core/otel/event-registry.ts
  • tests/.coverage-registry.json
  • tests/integration/t-coverage-mechanism-ratchet.test.ts
  • tests/integration/t413-no-silent-drop-ci-adoption.test.ts
  • tests/no-silent-drop/approval.json
  • tests/unit/t487-question-route-derivation.test.ts

main took t486 and t487 while this branch was in review, so the two
tests here move up to t488/t489 and every reference follows. The
mechanism ratchet lists both sides' spawners.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@tests/.coverage-registry.json`:
- Line 6235: Update the QUESTION_ANSWERED audit entry in
tests/.coverage-registry.json, not just the subcommand registration for
t488-question-route-observability.integration.test.ts. Add that integration test
to QUESTION_ANSWERED.coveredBy and change its status from UNCOVERED to covered,
preserving the existing audit coverage structure.
🪄 Autofix

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: ASSERTIVE

Plan: Pro Plus

Run ID: 4f17c6ff-e702-4dfb-b841-a8aeb52ec61d

📥 Commits

Reviewing files that changed from the base of the PR and between 4ad0549 and 1a989ea.

📒 Files selected for processing (4)
  • tests/.coverage-registry.json
  • tests/integration/t-coverage-mechanism-ratchet.test.ts
  • tests/integration/t488-question-route-observability.integration.test.ts
  • tests/unit/t489-question-route-derivation.test.ts

"minMechanism": "cli",
"coveredBy": [
{
"file": "tests/integration/t488-question-route-observability.integration.test.ts",

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🗄️ Data Integrity & Integration | 🟡 Minor | ⚡ Quick win

QUESTION_ANSWERED の監査単位も更新してください。

tests/integration/t488-question-route-observability.integration.test.tsQUESTION_ANSWERED を生成します。現在の QUESTION_ANSWERED エントリは Line [519]-[523] で coveredBy: []UNCOVERED のままです。Line [6235] のサブコマンド登録だけでは、監査イベントのカバレッジ証跡が更新されません。

同じテストを QUESTION_ANSWERED.coveredBy に追加し、実際の機構に合わせて statuscovered に更新してください。

修正例
  "unitId": "QUESTION_ANSWERED",
  "coveredBy": [
+   {
+     "file": "tests/integration/t488-question-route-observability.integration.test.ts",
+     "mechanism": "cli"
+   }
  ],
- "status": "UNCOVERED"
+ "status": "covered"
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@tests/.coverage-registry.json` at line 6235, Update the QUESTION_ANSWERED
audit entry in tests/.coverage-registry.json, not just the subcommand
registration for t488-question-route-observability.integration.test.ts. Add that
integration test to QUESTION_ANSWERED.coveredBy and change its status from
UNCOVERED to covered, preserving the existing audit coverage structure.

@j5ik2o
j5ik2o merged commit e0e5d7e into main Aug 8, 2026
15 checks passed
@j5ik2o
j5ik2o deleted the bolt-2378-u3-question-route branch August 8, 2026 04:26
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.

1 participant