use axum::{ extract::{Path, State}, routing::{delete, get, post}, Json, Router, }; use serde::Deserialize; use crate::state::AppState; pub fn routes() -> Router { Router::new() .route("/messages/send", post(send_message)) .route("/messages/poll/{fingerprint}", get(poll_messages)) .route("/messages/{id}/ack", delete(ack_message)) } #[derive(Deserialize)] struct SendRequest { to: String, message: Vec, // bincode-serialized WarzoneMessage } async fn send_message( State(state): State, Json(req): Json, ) -> Json { // Append to recipient's queue let key = format!("queue:{}", req.to); let _ = state.db.messages.insert( format!("{}:{}", key, uuid::Uuid::new_v4()).as_bytes(), req.message, ); Json(serde_json::json!({ "ok": true })) } async fn poll_messages( State(state): State, Path(fingerprint): Path, ) -> Json> { let prefix = format!("queue:{}", fingerprint); let mut messages = Vec::new(); for item in state.db.messages.scan_prefix(prefix.as_bytes()) { if let Ok((_, value)) = item { messages.push(base64::Engine::encode( &base64::engine::general_purpose::STANDARD, &value, )); } } Json(messages) } async fn ack_message( State(state): State, Path(id): Path, ) -> Json { // Scan for and remove the message with this ID // In a real implementation, we'd have a proper index let _ = state.db.messages.remove(id.as_bytes()); Json(serde_json::json!({ "ok": true })) }