use crate::contracts::{UniversalRequest, UniversalResponse};
use crate::identity::{EngineId, EngineInstanceId};
use crate::transport::{BoxedFuture, TransportError};
#[derive(Clone, Copy, Debug, Eq, PartialEq)]
pub enum ClientConnectionState {
Connecting,
Open,
Closing,
Closed,
}
impl ClientConnectionState {
pub fn is_open(&self) -> bool {
matches!(self, ClientConnectionState::Open)
}
}
pub trait ClientConnection: Send + Sync {
fn peer_engine(&self) -> &EngineId;
fn peer_instance(&self) -> &EngineInstanceId;
fn state(&self) -> ClientConnectionState;
fn call(&self, request: UniversalRequest) -> BoxedFuture<UniversalResponse, TransportError>;
fn close(&mut self);
}
pub trait ClientConnectionFactory: Send + Sync {
fn connect(
&self,
target: &EngineInstanceId,
) -> BoxedFuture<Box<dyn ClientConnection>, TransportError>;
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn client_connection_state_transitions_are_correct() {
assert!(!ClientConnectionState::Connecting.is_open());
assert!(ClientConnectionState::Open.is_open());
assert!(!ClientConnectionState::Closing.is_open());
assert!(!ClientConnectionState::Closed.is_open());
}
#[test]
fn client_connection_state_is_open_only_when_open() {
let open_state = ClientConnectionState::Open;
let connecting_state = ClientConnectionState::Connecting;
let closing_state = ClientConnectionState::Closing;
let closed_state = ClientConnectionState::Closed;
assert!(open_state.is_open());
assert!(!connecting_state.is_open());
assert!(!closing_state.is_open());
assert!(!closed_state.is_open());
}
}