bert-agent / daemon /src /types.rs
SNAPKITTYWEST's picture
push from SNAPKITTYWEST/bert-agent
30f011f verified
Raw
History Blame Contribute Delete
3.16 kB
//! types.rs — shared types for the inference daemon
use serde::{Deserialize, Serialize};
use tokio::sync::oneshot;
/// A single (claim, chunk) verification request.
/// `responder` routes the result back to the caller without polling.
pub struct VerifyRequest {
pub input_ids: Vec<i64>,
pub attention_mask: Vec<i64>,
pub token_type_ids: Vec<i64>,
pub chunk_id: String, // canonical ID of the retrieved source chunk
pub claim_text: String, // exact LLM-generated claim string
pub responder: oneshot::Sender<VerifyResponse>,
}
/// Response returned through the oneshot channel.
#[derive(Debug, Clone)]
pub struct VerifyResponse {
pub entailment_score: f32, // softmax P(Entailment)
pub label: Verdict,
pub attestation_hash: [u8; 32], // BLAKE3 hash of the serialised attestation
}
#[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize)]
pub enum Verdict {
Entailment,
Neutral,
Contradiction,
}
impl Verdict {
pub fn from_score(score: f32, threshold: f32) -> Self {
if score >= threshold {
Verdict::Entailment
} else {
Verdict::Contradiction // scores below threshold are rejected
}
}
}
/// Deterministically serialisable attestation record.
/// bincode serialises this to a canonical byte string before BLAKE3 hashing.
#[derive(Debug, Serialize, Deserialize)]
pub struct EntailmentAttestation {
pub timestamp_ns: u64,
pub chunk_id: String,
pub claim_text: String,
pub entailment_score: f32,
pub verdict: String,
pub model_signature: String, // e.g. "deberta-v3-fp16-v1.2"
pub threshold: f32,
}
impl EntailmentAttestation {
/// Serialise deterministically with bincode and compute BLAKE3 hash.
pub fn seal(&self) -> ([u8; 32], Vec<u8>) {
let payload = bincode::serialize(self)
.expect("bincode serialisation is infallible for flat structs");
let hash: [u8; 32] = *blake3::hash(&payload).as_bytes();
(hash, payload)
}
}
/// Daemon configuration loaded from config/daemon.json.
#[derive(Debug, Clone, Deserialize)]
pub struct DaemonConfig {
pub model_path: String,
pub trt_cache_dir: String,
pub threshold: f32, // entailment rejection threshold from calibrate.py
pub max_batch_size: usize,
pub flush_interval_ms: u64,
pub model_signature: String,
pub http_port: u16,
pub ledger_path: String, // WORM ledger file path
}
impl Default for DaemonConfig {
fn default() -> Self {
Self {
model_path: "./onnx/cross_encoder_opt_fp16.onnx".into(),
trt_cache_dir: "./trt_cache".into(),
threshold: 0.85,
max_batch_size: 32,
flush_interval_ms: 5,
model_signature: "deberta-v3-fp16-v1.2".into(),
http_port: 8080,
ledger_path: "./ledger/audit_chain.db".into(),
}
}
}