#![allow(dead_code)]
use serde::{Deserialize, Serialize};
#[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize, Deserialize)]
pub enum DoctorFix {
RebuildVectorIndex,
RotateHmacKey,
RepinMcpCatalog,
EnableDecayLane,
UpgradeRmcp,
}
impl DoctorFix {
pub fn as_str(&self) -> &'static str {
match self {
DoctorFix::RebuildVectorIndex => "rebuild_vector_index",
DoctorFix::RotateHmacKey => "rotate_hmac_key",
DoctorFix::RepinMcpCatalog => "repin_mcp_catalog",
DoctorFix::EnableDecayLane => "enable_decay_lane",
DoctorFix::UpgradeRmcp => "upgrade_rmcp",
}
}
}
#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
pub struct DoctorReport {
pub duckdb_ok: bool,
pub hmac_chain_intact: bool,
pub mcp_catalog_pinned: bool,
pub mesh_identity_present: Option<bool>,
pub recall_p50_ms: f32,
pub fixes: Vec<DoctorFix>,
}
impl DoctorReport {
pub fn build(
duckdb_ok: bool,
hmac_chain_intact: bool,
mcp_catalog_pinned: bool,
mesh_identity_present: Option<bool>,
recall_p50_ms: f32,
) -> Self {
let mut fixes = Vec::new();
if !duckdb_ok {
fixes.push(DoctorFix::RebuildVectorIndex);
}
if !hmac_chain_intact {
fixes.push(DoctorFix::RotateHmacKey);
}
if !mcp_catalog_pinned {
fixes.push(DoctorFix::RepinMcpCatalog);
}
if recall_p50_ms > 50.0 {
fixes.push(DoctorFix::EnableDecayLane);
}
Self {
duckdb_ok,
hmac_chain_intact,
mcp_catalog_pinned,
mesh_identity_present,
recall_p50_ms,
fixes,
}
}
pub fn is_clean(&self) -> bool {
self.fixes.is_empty()
}
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn clean_install_reports_no_fixes() {
let r = DoctorReport::build(true, true, true, Some(true), 5.0);
assert!(r.is_clean());
assert!(r.fixes.is_empty());
}
#[test]
fn broken_chain_recommends_rotate() {
let r = DoctorReport::build(true, false, true, None, 5.0);
assert!(r.fixes.contains(&DoctorFix::RotateHmacKey));
}
#[test]
fn slow_recall_suggests_decay_lane() {
let r = DoctorReport::build(true, true, true, None, 75.0);
assert!(r.fixes.contains(&DoctorFix::EnableDecayLane));
}
#[test]
fn fix_strings_round_trip() {
for f in [
DoctorFix::RebuildVectorIndex,
DoctorFix::RotateHmacKey,
DoctorFix::RepinMcpCatalog,
DoctorFix::EnableDecayLane,
DoctorFix::UpgradeRmcp,
] {
assert!(!f.as_str().is_empty());
}
}
}