返回 CodeWhale
diagnostics_tools.rs
根目录 / crates / command-contract / src / facets / diagnostics_tools.rs
1 //! Bounded, structured prepared-tool evidence for `/tools`.
2 //!
3 //! The host captures and classifies facts using the existing inspector.
4 //! These data-only projections retain its JSON schema, including explicit
5 //! unknown states. Text and JSON rendering remain portable and single-owned.
6
7 use serde::Serialize;
8
9 #[derive(Debug, Clone, PartialEq, Serialize)]
10 pub struct DebugBoundedString {
11 pub value: String,
12 pub truncated: bool,
13 }
14
15 #[derive(Debug, Clone, PartialEq, Serialize)]
16 #[serde(tag = "status", rename_all = "snake_case")]
17 pub enum DebugEvidence<T> {
18 Known { value: T },
19 Unknown { reason: String },
20 }
21
22 #[derive(Debug, Clone, PartialEq, Serialize)]
23 pub struct DebugBoundedList {
24 pub count: usize,
25 pub rendered: Vec<DebugBoundedString>,
26 pub omitted: usize,
27 }
28
29 #[derive(Debug, Clone, PartialEq, Serialize)]
30 pub struct DebugCountOnly {
31 pub count: usize,
32 pub values: String,
33 }
34
35 #[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize)]
36 #[serde(rename_all = "snake_case")]
37 pub enum DebugToolProvenance {
38 Builtin,
39 Plugin,
40 Mcp,
41 Synthetic,
42 Unknown,
43 }
44
45 #[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize)]
46 #[serde(rename_all = "snake_case")]
47 pub enum DebugToolVisibility {
48 Active,
49 Deferred,
50 InRequest,
51 }
52
53 #[derive(Debug, Clone, PartialEq, Eq, Serialize)]
54 #[serde(tag = "status", rename_all = "snake_case")]
55 pub enum DebugProviderAvailability {
56 Unknown,
57 Available { provider: String, model: String },
58 Unavailable { reason: String },
59 }
60
61 #[derive(Debug, Clone, PartialEq, Serialize)]
62 pub struct DebugToolProjection {
63 pub ordinal: usize,
64 pub name: DebugBoundedString,
65 pub tool_type: DebugEvidence<DebugBoundedString>,
66 pub description: DebugBoundedString,
67 pub input_schema_json: DebugBoundedString,
68 pub allowed_callers: DebugEvidence<DebugBoundedList>,
69 pub defer_loading: DebugEvidence<bool>,
70 pub input_examples: DebugEvidence<DebugCountOnly>,
71 pub strict: DebugEvidence<bool>,
72 pub cache_control_type: DebugEvidence<DebugBoundedString>,
73 pub provenance: DebugEvidence<DebugToolProvenance>,
74 pub mcp_server: DebugEvidence<DebugBoundedString>,
75 pub capabilities: DebugEvidence<DebugBoundedList>,
76 pub approval: DebugEvidence<DebugBoundedString>,
77 pub model_visible: DebugEvidence<bool>,
78 pub visibility: DebugToolVisibility,
79 }
80
81 #[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize)]
82 #[serde(rename_all = "snake_case")]
83 pub enum DebugTurnOutcomeStatus {
84 Completed,
85 Interrupted,
86 Failed,
87 }
88
89 #[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize)]
90 #[serde(rename_all = "snake_case")]
91 pub enum DebugTurnStopReason {
92 ProviderNoToolCall,
93 ProviderToolCallMissing,
94 StepBudgetExhausted,
95 NoProgress,
96 Interrupted,
97 Failed,
98 }
99
100 /// Precise, terminal facts: every optional counter retains unknown vs zero.
101 #[derive(Debug, Clone, PartialEq, Serialize)]
102 pub struct DebugTurnStopDiagnostics {
103 pub status: Option<DebugTurnOutcomeStatus>,
104 pub reason: Option<DebugTurnStopReason>,
105 pub effective_max_steps: Option<u32>,
106 pub step_budget_source: String,
107 pub model_step_index: u32,
108 pub model_requests_started: u32,
109 pub transport_retries: u32,
110 pub transparent_stream_retries: u32,
111 pub stream_resumes: u32,
112 pub reasoning_only_reprompts: u32,
113 pub empty_stop_retries: u32,
114 pub soft_landing_sent: bool,
115 pub final_report_requested: bool,
116 pub permission_strategy_switches: u32,
117 pub permission_denial_rounds_without_progress: u32,
118 pub last_provider_finish_reason: Option<DebugBoundedString>,
119 pub last_response_tool_calls: Option<usize>,
120 pub last_response_tool_calls_suppressed: Option<usize>,
121 pub last_reported_input_tokens: Option<u32>,
122 pub route_context_window_tokens: Option<u64>,
123 pub last_prepared_output_limit_tokens: Option<u32>,
124 pub automatic_compaction_attempts: u32,
125 pub emergency_compaction_attempts: u32,
126 }
127
128 /// One frozen prepared-request snapshot; no registry or client reference.
129 #[derive(Debug, Clone, PartialEq, Serialize)]
130 pub struct DebugToolSnapshot {
131 pub schema_version: u32,
132 pub capture_source: String,
133 pub delivery_status: String,
134 pub turn_id: DebugBoundedString,
135 pub step: u32,
136 #[serde(skip_serializing_if = "Option::is_none")]
137 pub terminal: Option<DebugTurnStopDiagnostics>,
138 pub tools_field_present: bool,
139 pub tool_count: usize,
140 pub rendered_tool_count: usize,
141 pub omitted_tool_count: usize,
142 pub payload_json_bytes: Option<usize>,
143 pub payload_measurement_status: String,
144 pub active_tool_catalog_sha256: Option<String>,
145 pub unavailable_for_this_request: Vec<String>,
146 pub provider: DebugProviderAvailability,
147 pub registry_facts_present: bool,
148 pub registry_tool_count: DebugEvidence<usize>,
149 pub registry_only_tools: DebugEvidence<DebugBoundedList>,
150 pub tools: Vec<DebugToolProjection>,
151 }
152
152 lines RUST