use async_trait::async_trait;
use execution_engine::{
EventHandler, ExecutionConfig, ExecutionEngine, ExecutionEvent, ExecutionRequest,
};
use std::future::Future;
use std::io::{BufRead, Write};
use std::pin::Pin;
use std::sync::{Arc, Mutex};
struct JsonBridgeHandler {
stdout: Arc<Mutex<std::io::Stdout>>,
}
impl EventHandler for JsonBridgeHandler {
fn handle_event<'life0, 'async_trait>(
&'life0 self,
event: ExecutionEvent,
) -> Pin<Box<dyn Future<Output = ()> + Send + 'async_trait>>
where
'life0: 'async_trait,
Self: 'async_trait,
{
Box::pin(async move {
#[derive(serde::Serialize)]
struct BridgeEvent {
r#type: String,
payload: ExecutionEvent,
}
let bridge_event = BridgeEvent {
r#type: "event".to_string(),
payload: event,
};
if let Ok(json) = serde_json::to_string(&bridge_event) {
let result = {
let mut stdout = self.stdout.lock().unwrap();
let res = writeln!(stdout, "{}", json);
let _ = stdout.flush();
res
};
let _ = result;
}
})
}
}
#[tokio::main]
async fn main() {
let config = ExecutionConfig::default();
let stdout_mutex = Arc::new(Mutex::new(std::io::stdout()));
let handler = Arc::new(JsonBridgeHandler {
stdout: stdout_mutex,
});
match ExecutionEngine::init_global_with_handler(config, Some(handler)) {
Ok(_) => {}
Err(e) => {
eprintln!("Failed to initialize engine: {}", e);
std::process::exit(1);
}
}
let engine = ExecutionEngine::global();
let stdin = std::io::stdin();
let mut stdout = std::io::stdout(); let mut handle = stdin.lock();
let mut line = String::new();
eprintln!("JSON Bridge Ready. Send ExecutionRequest JSON on stdin.");
while handle.read_line(&mut line).unwrap() > 0 {
if line.trim().is_empty() {
line.clear();
continue;
}
match serde_json::from_str::<ExecutionRequest>(&line) {
Ok(request) => {
eprintln!("Received request: {}", request.id);
match engine.execute(request.clone()).await {
Ok(id) => {
match engine.wait_for_completion(id).await {
Ok(result) => {
#[derive(serde::Serialize)]
struct BridgeResponse {
r#type: String,
payload: execution_engine::ExecutionResult,
}
let response = BridgeResponse {
r#type: "result".to_string(),
payload: result,
};
let json = serde_json::to_string(&response).unwrap();
writeln!(stdout, "{}", json).unwrap();
stdout.flush().unwrap();
}
Err(e) => {
send_error(&mut stdout, &request.id.to_string(), &e.to_string());
}
}
}
Err(e) => {
send_error(&mut stdout, &request.id.to_string(), &e.to_string());
}
}
}
Err(e) => {
eprintln!("Failed to parse request: {}", e);
}
}
line.clear();
}
}
fn send_error(stdout: &mut std::io::Stdout, id: &str, error: &str) {
let error_json = serde_json::json!({
"type": "error",
"payload": {
"id": id,
"error": error
}
});
writeln!(stdout, "{}", error_json).unwrap();
stdout.flush().unwrap();
}