mod common;
use serde_json::json;
use common::{connect, slot_for, spawn_upstream, UpstreamConfig, LETTERS};
use jev_bridge::strategy::Probe;
use jev_bridge::wire::{Row, RowOption};
fn two_option_row() -> Row {
Row {
id: "row".to_string(),
state: json!("I was charged twice."),
question: "Which queue?".to_string(),
options: vec![
RowOption {
id: "billing".to_string(),
description: "Refunds.".to_string(),
},
RowOption {
id: "sales".to_string(),
description: "Pricing.".to_string(),
},
],
}
}
fn sixteen_option_row() -> Row {
Row {
id: "row".to_string(),
state: json!("The customer cannot log in."),
question: "Which bucket fits best?".to_string(),
options: (0..16)
.map(|index| RowOption {
id: format!("opt{index:02}"),
description: format!("Bucket {index}"),
})
.collect(),
}
}
#[tokio::test]
async fn probe_picks_the_completions_path_and_resolves_all_sixteen_slots() {
let upstream = spawn_upstream(UpstreamConfig::default()).await;
let bridge = connect(&upstream).await.unwrap();
assert_eq!(bridge.probe(), Probe::CompletionsTopK);
let expected: Vec<u32> = LETTERS.chars().map(slot_for).collect();
assert_eq!(bridge.slots(), expected.as_slice());
}
#[tokio::test]
async fn detailed_scores_expose_logprobs_and_prompt_hash() {
let upstream = spawn_upstream(UpstreamConfig::default()).await;
let bridge = connect(&upstream).await.unwrap();
let scored = bridge.score_row(&two_option_row()).await.unwrap();
let first = &scored;
assert_eq!(first.answer.id, "row");
assert_eq!(first.answer.option_ids, vec!["billing", "sales"]);
assert_eq!(first.option_logprobs, vec![-1.0, -2.0]);
assert!(first.answer.probabilities[0] > first.answer.probabilities[1]);
assert_eq!(first.answer.input_tokens, 42);
assert_eq!(first.prompt_sha256.len(), 64);
assert_eq!(
first.answer.prompt_version.as_deref(),
Some("direct-options-v1")
);
}
#[tokio::test]
async fn sixteen_option_decision_is_scored_from_one_prompt() {
let upstream = spawn_upstream(UpstreamConfig::default()).await;
let bridge = connect(&upstream).await.unwrap();
let scored = bridge.score_row(&sixteen_option_row()).await.unwrap();
let probabilities = &scored.answer.probabilities;
assert_eq!(probabilities.len(), 16);
let total: f64 = probabilities.iter().sum();
assert!((total - 1.0).abs() < 1e-9, "{total}");
assert!(probabilities[0] > probabilities[15]);
}