use std::collections::HashMap;
use serde::{Deserialize, Serialize};
use uuid::Uuid;
use super::capabilities::{CommunicationDirection, CommunicationInitiator, ServerInitiatedType};
use super::client::ClientCapabilities;
use crate::types::Timestamp;
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct BidirectionalContext {
pub direction: CommunicationDirection,
pub initiator: CommunicationInitiator,
pub expects_response: bool,
pub parent_request_id: Option<String>,
pub request_type: Option<String>,
pub server_id: Option<String>,
pub correlation_id: String,
pub metadata: HashMap<String, serde_json::Value>,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct ServerInitiatedContext {
pub request_type: ServerInitiatedType,
pub server_id: String,
pub correlation_id: String,
pub client_capabilities: Option<ClientCapabilities>,
pub initiated_at: Timestamp,
pub metadata: HashMap<String, serde_json::Value>,
}
impl BidirectionalContext {
pub fn new(direction: CommunicationDirection, initiator: CommunicationInitiator) -> Self {
Self {
direction,
initiator,
expects_response: true,
parent_request_id: None,
request_type: None,
server_id: None,
correlation_id: Uuid::new_v4().to_string(),
metadata: HashMap::new(),
}
}
pub fn with_direction(mut self, direction: CommunicationDirection) -> Self {
self.direction = direction;
self
}
pub fn with_request_type(mut self, request_type: String) -> Self {
self.request_type = Some(request_type);
self
}
pub fn validate_direction(&self) -> Result<(), String> {
match (&self.direction, &self.initiator) {
(CommunicationDirection::ClientToServer, CommunicationInitiator::Client) => Ok(()),
(CommunicationDirection::ServerToClient, CommunicationInitiator::Server) => Ok(()),
_ => Err("Invalid direction/initiator combination".to_string()),
}
}
}
impl ServerInitiatedContext {
pub fn new(request_type: ServerInitiatedType, server_id: String) -> Self {
Self {
request_type,
server_id,
correlation_id: Uuid::new_v4().to_string(),
client_capabilities: None,
initiated_at: Timestamp::now(),
metadata: HashMap::new(),
}
}
pub fn with_capabilities(mut self, capabilities: ClientCapabilities) -> Self {
self.client_capabilities = Some(capabilities);
self
}
pub fn with_metadata(mut self, key: String, value: serde_json::Value) -> Self {
self.metadata.insert(key, value);
self
}
}