#![allow(clippy::unwrap_used, clippy::expect_used, clippy::panic_in_result_fn)]
use clap::Parser;
use log::error;
use mosaik_api::tcp::ConnectionDirection;
use mosaik_api::types::{
Attr, CreateResult, EntityId, InputData, Meta, ModelDescription, OutputData, OutputRequest,
SimId, SimulatorType, Time,
};
use mosaik_api::{run_simulation, MosaikApi};
use serde_json::{json, Map, Value};
use std::collections::HashMap;
use std::sync::LazyLock;
static META: LazyLock = LazyLock::new(|| {
Meta::new(
SimulatorType::EventBased,
HashMap::from([(
"Agent".to_string(),
ModelDescription {
public: true,
params: &[],
attrs: &["val_in", "delta"],
trigger: None,
any_inputs: None,
persistent: None,
},
)]),
None,
)
});
// A simple demo controller. Inspired by the python tutorial
#[derive(Default)]
pub struct Controller {
agents: Vec,
data: HashMap>,
time: Time,
}
impl MosaikApi for Controller {
fn init(
&mut self,
_sid: SimId,
_time_resolution: f64,
_sim_params: Map,
) -> Result<&'static Meta, String> {
Ok(&META)
}
fn create(
&mut self,
num: usize,
model_name: String,
_model_params: Map,
) -> Result, String> {
let n_agents = self.agents.len();
let mut entities: Vec = vec![];
for i in n_agents..(n_agents + num) {
let eid = format!("Agent_{i}");
self.agents.push(eid.clone());
entities.push(CreateResult {
eid,
model_type: model_name.clone(),
rel: None,
children: None,
extra_info: None,
});
}
Ok(entities)
}
fn setup_done(&self) -> Result<(), String> {
Ok(())
}
fn stop(&self) {}
fn step(
&mut self,
time: Time,
inputs: InputData,
_max_advance: Time,
) -> Result