use metacrate_grid_agent::{ ACCEPTANCE_SCHEMA_VERSION, ACCEPTANCE_SECRET_CANARY, AcceptanceBudgets, AcceptanceEvidenceWriter, AcceptanceRecord, AcceptanceStatus, LiveGridOptIns, run_deterministic_acceptance, }; use std::collections::BTreeMap; use std::fs; use std::path::PathBuf; use std::time::{SystemTime, UNIX_EPOCH}; fn temporary(name: &str) -> PathBuf { std::env::temp_dir().join(format!( "metacrate-acceptance-{}-{name}", SystemTime::now() .duration_since(UNIX_EPOCH) .unwrap() .as_nanos() )) } #[tokio::test] async fn deterministic_gate_writes_ordered_redacted_evidence_and_drains() { let path = temporary("gate.jsonl"); run_deterministic_acceptance(&path, AcceptanceBudgets::default()) .await .expect("acceptance gate"); let text = fs::read_to_string(&path).expect("evidence"); assert!(!text.contains(ACCEPTANCE_SECRET_CANARY)); let records = text .lines() .map(|line| serde_json::from_str::(line).expect("record")) .collect::>(); assert_eq!(records.len(), 7); assert!( records .iter() .all(|record| record.status == AcceptanceStatus::Passed) ); assert_eq!( records .iter() .map(|record| record.sequence) .collect::>(), vec![1, 2, 3, 4, 5, 6, 7] ); for required in [ "headless_startup", "control_conformance", "chat_scheduling", "clean_shutdown", "maintenance_reconnect", "policy_redaction_and_protocol_audit", ] { assert!(records.iter().any(|record| record.stage == required)); } assert!( run_deterministic_acceptance(&path, AcceptanceBudgets::default()) .await .is_err(), "evidence is never overwritten" ); fs::remove_file(path).unwrap(); } #[test] fn live_actions_require_exact_independent_confirmations() { let mut values = BTreeMap::new(); values.insert("METACRATE_AGENT_LIVE_CHAT_IM", "CHAT-IM"); let action_without_login = LiveGridOptIns::from_environment(|name| values.get(name).map(ToString::to_string)); assert!(action_without_login.validate().is_err()); values.insert("METACRATE_AGENT_LIVE_LOGIN", "LOGIN"); values.insert("METACRATE_AGENT_LIVE_BUILD", "wrong"); let confirmed = LiveGridOptIns::from_environment(|name| values.get(name).map(ToString::to_string)) .validate() .unwrap(); assert!(confirmed.login && confirmed.chat_and_im); assert!(!confirmed.reversible_build); } #[test] fn evidence_writer_rejects_secret_markers_and_schema_is_committed() { let path = temporary("unsafe.jsonl"); let mut writer = AcceptanceEvidenceWriter::create(&path).unwrap(); let record = AcceptanceRecord { schema_version: ACCEPTANCE_SCHEMA_VERSION, sequence: 1, unix_millis: 0, package_version: "test".into(), source_revision: "test".into(), rust_toolchain: "test".into(), command: "test".into(), profile: "test".into(), grid_type: "test".into(), endpoint_capabilities: Vec::new(), stage: "canary".into(), status: AcceptanceStatus::Failed, duration_millis: 0, budget_millis: None, outcome_code: ACCEPTANCE_SECRET_CANARY.into(), evidence_sha256: "0".repeat(64), metrics: serde_json::Map::new(), limitations: Vec::new(), }; assert!(writer.write(&record).is_err()); drop(writer); fs::remove_file(path).unwrap(); let workspace = PathBuf::from(env!("CARGO_MANIFEST_DIR")).join("../.."); let schema = fs::read_to_string(workspace.join("config/grid-agent-acceptance-evidence.schema.json")) .unwrap(); let schema: serde_json::Value = serde_json::from_str(&schema).unwrap(); assert_eq!( schema["properties"]["schema_version"]["const"], ACCEPTANCE_SCHEMA_VERSION ); let report = fs::read_to_string(workspace.join("docs/grid-agent-acceptance.md")).unwrap(); for required in [ "Deterministic gate", "Live-grid matrix", "Resource budgets", "Remaining limitations", "#128", "#134", ] { assert!(report.contains(required), "report missing {required}"); } }