use serde::{Deserialize, Serialize};
pub const CLEAN_SENTINEL: &str = "No material findings.";
pub const LANE_CLEAN_SENTINEL: &str = "No findings.";
#[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize)]
#[serde(tag = "verdict", rename_all = "snake_case")]
pub enum ReviewVerdict {
Findings {
synthesis: String,
#[serde(default)]
evidence: ReviewPassEvidence,
},
Clean,
Failed { reason: String },
}
impl ReviewVerdict {
#[must_use]
pub const fn is_clean(&self) -> bool {
matches!(self, Self::Clean)
}
}
#[derive(Debug, Clone, Default, PartialEq, Eq, Serialize, Deserialize)]
#[serde(default)]
pub struct ReviewPassEvidence {
pub intent_brief: String,
pub intent_available: bool,
pub lanes: Vec<ReviewLaneEvidence>,
}
#[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize)]
pub struct ReviewLaneEvidence {
pub id: String,
pub outcome: LaneOutcome,
}
#[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize)]
#[serde(tag = "outcome", rename_all = "snake_case")]
pub enum LaneOutcome {
Completed,
Cancelled,
Failed { reason: String },
}
impl LaneOutcome {
#[must_use]
pub fn describe(&self) -> String {
match self {
Self::Completed => "completed".to_string(),
Self::Cancelled => "cancelled".to_string(),
Self::Failed { reason } => format!("failed: {reason}"),
}
}
}