Skip to main content

oxirs_physics/simulation/
mod.rs

1//! Physics Simulation Orchestration
2
3pub mod parameter_extraction;
4pub mod result_injection;
5pub mod samm_parser;
6pub mod scirs2_thermal;
7pub mod simulation_runner;
8
9pub use parameter_extraction::{ParameterExtractor, SimulationParameters};
10pub use result_injection::{ResultInjector, SimulationResult};
11pub use samm_parser::{AspectModel, SammParser};
12pub use scirs2_thermal::SciRS2ThermalSimulation;
13pub use simulation_runner::{PhysicsSimulation, SimulationRunner};
14
15use crate::error::{PhysicsError, PhysicsResult};
16use std::collections::HashMap;
17use std::sync::Arc;
18
19/// Simulation Orchestrator - coordinates parameter extraction, simulation, and result injection
20pub struct SimulationOrchestrator {
21    extractor: Arc<ParameterExtractor>,
22    injector: Arc<ResultInjector>,
23    simulations: HashMap<String, Arc<dyn PhysicsSimulation>>,
24}
25
26impl SimulationOrchestrator {
27    /// Create a new orchestrator
28    pub fn new() -> Self {
29        Self {
30            extractor: Arc::new(ParameterExtractor::new()),
31            injector: Arc::new(ResultInjector::new()),
32            simulations: HashMap::new(),
33        }
34    }
35
36    /// Register a simulation type
37    pub fn register(&mut self, name: impl Into<String>, simulation: Arc<dyn PhysicsSimulation>) {
38        self.simulations.insert(name.into(), simulation);
39    }
40
41    /// Extract parameters from RDF graph
42    pub async fn extract_parameters(
43        &self,
44        entity_iri: &str,
45        simulation_type: &str,
46    ) -> PhysicsResult<SimulationParameters> {
47        self.extractor.extract(entity_iri, simulation_type).await
48    }
49
50    /// Run simulation
51    pub async fn run(
52        &self,
53        simulation_type: &str,
54        params: SimulationParameters,
55    ) -> PhysicsResult<SimulationResult> {
56        let simulation = self.simulations.get(simulation_type).ok_or_else(|| {
57            PhysicsError::Simulation(format!("Unknown simulation type: {}", simulation_type))
58        })?;
59
60        simulation.run(&params).await
61    }
62
63    /// Inject results back to RDF
64    pub async fn inject_results(&self, result: &SimulationResult) -> PhysicsResult<()> {
65        self.injector.inject(result).await
66    }
67
68    /// Full simulation workflow: extract → run → inject
69    pub async fn execute_workflow(
70        &self,
71        entity_iri: &str,
72        simulation_type: &str,
73    ) -> PhysicsResult<SimulationResult> {
74        let params = self.extract_parameters(entity_iri, simulation_type).await?;
75        let result = self.run(simulation_type, params).await?;
76        self.inject_results(&result).await?;
77        Ok(result)
78    }
79}
80
81impl Default for SimulationOrchestrator {
82    fn default() -> Self {
83        Self::new()
84    }
85}
86
87#[cfg(test)]
88mod tests {
89    use super::*;
90
91    #[test]
92    fn test_orchestrator_creation() {
93        let orchestrator = SimulationOrchestrator::new();
94        assert!(orchestrator.simulations.is_empty());
95    }
96}