183 lines
5.7 KiB
Rust
183 lines
5.7 KiB
Rust
use std::fs;
|
|
|
|
use serde::Deserialize;
|
|
|
|
#[derive(Debug, Deserialize)]
|
|
struct G1ECandidateBatch {
|
|
#[serde(rename = "batchId")]
|
|
batch_id: String,
|
|
family: String,
|
|
source: String,
|
|
#[serde(rename = "supportingSources")]
|
|
supporting_sources: Vec<String>,
|
|
#[serde(rename = "ledgerClusterLabel")]
|
|
ledger_cluster_label: String,
|
|
#[serde(rename = "selectionRule")]
|
|
selection_rule: String,
|
|
#[serde(rename = "candidateCount")]
|
|
candidate_count: u32,
|
|
#[serde(rename = "representativeBaseline")]
|
|
representative_baseline: String,
|
|
#[serde(rename = "promotedBatchExpansionBaselines")]
|
|
promoted_batch_expansion_baselines: Vec<PromotedExpansionBaseline>,
|
|
#[serde(rename = "expectedSharedContract")]
|
|
expected_shared_contract: SharedContract,
|
|
candidates: Vec<BatchCandidate>,
|
|
notes: Vec<String>,
|
|
}
|
|
|
|
#[derive(Debug, Deserialize)]
|
|
struct PromotedExpansionBaseline {
|
|
#[serde(rename = "fixtureDir")]
|
|
fixture_dir: String,
|
|
#[serde(rename = "sceneId")]
|
|
scene_id: String,
|
|
#[serde(rename = "sceneName")]
|
|
scene_name: String,
|
|
assertions: ExpansionAssertions,
|
|
}
|
|
|
|
#[derive(Debug, Deserialize)]
|
|
struct ExpansionAssertions {
|
|
#[serde(rename = "requiredMainRequest")]
|
|
required_main_request: String,
|
|
#[serde(rename = "requiredEnrichmentRequest")]
|
|
required_enrichment_request: String,
|
|
#[serde(rename = "requiredMergeJoinKey")]
|
|
required_merge_join_key: String,
|
|
#[serde(rename = "requiredMergeAggregateRule")]
|
|
required_merge_aggregate_rule: String,
|
|
#[serde(rename = "requiredOutputColumn")]
|
|
required_output_column: String,
|
|
}
|
|
|
|
#[derive(Debug, Deserialize)]
|
|
struct SharedContract {
|
|
archetype: String,
|
|
#[serde(rename = "requiredGateNames")]
|
|
required_gate_names: Vec<String>,
|
|
}
|
|
|
|
#[derive(Debug, Deserialize)]
|
|
struct BatchCandidate {
|
|
#[serde(rename = "sceneKey")]
|
|
scene_key: String,
|
|
#[serde(rename = "batchRole")]
|
|
batch_role: String,
|
|
status: String,
|
|
}
|
|
|
|
#[test]
|
|
fn g1e_candidate_batch_asset_is_actionable() {
|
|
let batch = load_batch();
|
|
|
|
assert_eq!(batch.batch_id, "g1e-light-enrichment-candidates-2026-04-18");
|
|
assert_eq!(batch.family, "G1-E");
|
|
assert!(batch.source.ends_with(".md"));
|
|
assert_eq!(batch.ledger_cluster_label, "g1e-light-enrichment-candidate");
|
|
assert!(batch.selection_rule.contains("Track B"));
|
|
assert_eq!(batch.candidate_count, 3);
|
|
assert!(batch
|
|
.representative_baseline
|
|
.ends_with("g1e_light_enrichment"));
|
|
assert_eq!(batch.promoted_batch_expansion_baselines.len(), 2);
|
|
assert_eq!(
|
|
batch.expected_shared_contract.archetype,
|
|
"single_request_enrichment"
|
|
);
|
|
assert!(batch
|
|
.expected_shared_contract
|
|
.required_gate_names
|
|
.iter()
|
|
.any(|item| item == "merge_plan_resolved"));
|
|
assert_eq!(batch.candidates.len() as u32, batch.candidate_count);
|
|
assert_eq!(batch.supporting_sources.len(), 2);
|
|
assert!(!batch.notes.is_empty());
|
|
}
|
|
|
|
#[test]
|
|
fn g1e_candidate_batch_keeps_promoted_entries_visible() {
|
|
let batch = load_batch();
|
|
|
|
let promoted = batch
|
|
.promoted_batch_expansion_baselines
|
|
.iter()
|
|
.find(|item| item.fixture_dir.ends_with("g1e_light_enrichment_expansion"))
|
|
.expect("expected promoted G1-E expansion baseline");
|
|
assert_eq!(
|
|
promoted.scene_id,
|
|
"p1-g1e-light-enrichment-expansion-report"
|
|
);
|
|
assert_eq!(
|
|
promoted.scene_name,
|
|
"P1 G1-E light enrichment expansion report"
|
|
);
|
|
assert_eq!(promoted.assertions.required_main_request, "getWkorderAll");
|
|
assert_eq!(
|
|
promoted.assertions.required_enrichment_request,
|
|
"queryMeterInfo"
|
|
);
|
|
assert_eq!(promoted.assertions.required_merge_join_key, "wkOrderNo");
|
|
assert_eq!(
|
|
promoted.assertions.required_merge_aggregate_rule,
|
|
"group_by:countyCodeName"
|
|
);
|
|
assert_eq!(
|
|
promoted.assertions.required_output_column,
|
|
"meterCapacityThisMonth"
|
|
);
|
|
let additional = batch
|
|
.promoted_batch_expansion_baselines
|
|
.iter()
|
|
.find(|item| {
|
|
item.fixture_dir
|
|
.ends_with("g1e_light_enrichment_additional")
|
|
})
|
|
.expect("expected additional G1-E expansion baseline");
|
|
assert_eq!(
|
|
additional.scene_id,
|
|
"p1-g1e-light-enrichment-additional-report"
|
|
);
|
|
assert_eq!(
|
|
additional.scene_name,
|
|
"P1 G1-E light enrichment additional report"
|
|
);
|
|
assert_eq!(additional.assertions.required_main_request, "getWkorderAll");
|
|
assert_eq!(
|
|
additional.assertions.required_enrichment_request,
|
|
"queryBusAcpt"
|
|
);
|
|
assert_eq!(additional.assertions.required_merge_join_key, "wkOrderNo");
|
|
assert_eq!(
|
|
additional.assertions.required_merge_aggregate_rule,
|
|
"group_by:countyCodeName"
|
|
);
|
|
assert_eq!(
|
|
additional.assertions.required_output_column,
|
|
"batchCapacityThisMonth"
|
|
);
|
|
|
|
assert!(batch.candidates.iter().any(|item| item.scene_key
|
|
== "high_low_voltage_new_capacity_monthly"
|
|
&& item.batch_role == "p0-anchor"
|
|
&& item.status == "promoted-baseline"));
|
|
assert!(batch
|
|
.candidates
|
|
.iter()
|
|
.any(|item| item.scene_key == "light_enrichment_second_sample"
|
|
&& item.batch_role == "first-expansion-anchor"
|
|
&& item.status == "promoted-expansion"));
|
|
assert!(batch.candidates.iter().any(|item| item.scene_key
|
|
== "light_enrichment_additional_real_sample"
|
|
&& item.batch_role == "second-expansion-anchor"
|
|
&& item.status == "promoted-expansion"));
|
|
}
|
|
|
|
fn load_batch() -> G1ECandidateBatch {
|
|
serde_json::from_str(
|
|
&fs::read_to_string("tests/fixtures/generated_scene/g1e_candidate_batch_2026-04-18.json")
|
|
.unwrap(),
|
|
)
|
|
.unwrap()
|
|
}
|