Skip to main content

qualia_cli/bench/
sparql_bench.rs

1use qualia_core_db::sparql_library::sparql_executor::QueryExecutor;
2use qualia_core_db::sparql_library::sparql_parser::parse_sparql;
3use qualia_core_db::sparql_library::sparql_planner::QueryPlanner;
4use qualia_core_db::NQuin;
5use std::path::Path;
6use std::time::Instant;
7
8#[derive(Debug)]
9pub enum BenchError {
10    Format(String),
11}
12
13impl std::fmt::Display for BenchError {
14    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
15        match self {
16            BenchError::Format(s) => write!(f, "{}", s),
17        }
18    }
19}
20impl std::error::Error for BenchError {}
21
22pub fn run_sparql_suite(database_volume_path: &Path) -> Result<(), BenchError> {
23    println!(
24        "Initializing Memory-Mapped Volume: {:?}",
25        database_volume_path
26    );
27    let start_init = Instant::now();
28
29    // The resident executor remains a benchmark compatibility path, but it
30    // opens a front-manifested logical root as one graph.
31    let all_quins: Vec<NQuin> = qualia_core_db::q42_reader::read_q42_quins(database_volume_path)
32        .map_err(|e| BenchError::Format(format!("Failed to open Q42 volume: {e}")))?;
33
34    println!(
35        "Volume loaded into memory: {} quins in {} μs",
36        all_quins.len(),
37        start_init.elapsed().as_micros()
38    );
39
40    let query_point_lookup = "
41        PREFIX yago: <http://yago-knowledge.org/resource/>
42        SELECT ?birthPlace ?date
43        WHERE {
44            yago:Albert_Einstein yago:wasBornIn ?birthPlace .
45            <<yago:Albert_Einstein yago:wasBornIn ?birthPlace>> yago:occurredOnDate ?date .
46        }
47    ";
48
49    println!("Running SPARQL-star Point Lookup Benchmark...");
50
51    let parse_timer = Instant::now();
52    let (ast, ctx) = parse_sparql(query_point_lookup).map_err(|e| BenchError::Format(e))?;
53    let plan = QueryPlanner::plan(&ast, &ctx).map_err(|e| BenchError::Format(e))?;
54    println!(
55        "Query compiled in: {} μs",
56        parse_timer.elapsed().as_micros()
57    );
58
59    let query_timer = Instant::now();
60    let executor = QueryExecutor::new(&all_quins);
61    let results = executor
62        .execute(&plan, &ctx)
63        .map_err(|e| BenchError::Format(e))?;
64    let latency = query_timer.elapsed();
65
66    println!(
67        "Query execution completed safely in: {} μs",
68        latency.as_micros()
69    );
70    println!("Found {} results.", results.len());
71    Ok(())
72}