use std::sync::Arc;
use crate::adapter::Adapter;
use crate::handler::{FromConnectParts, FromDisconnectParts, FromMessageParts};
use crate::socket::{DisconnectReason, Socket};
use socketioxide_core::Value;
pub struct State<T>(pub T);
pub struct StateNotFound<T>(std::marker::PhantomData<T>);
impl<T> std::fmt::Display for StateNotFound<T> {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
write!(
f,
"State of type {} not found, maybe you forgot to insert it in the state map?",
std::any::type_name::<T>()
)
}
}
impl<T> std::fmt::Debug for StateNotFound<T> {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
write!(f, "StateNotFound {}", std::any::type_name::<T>())
}
}
impl<T> std::error::Error for StateNotFound<T> {}
impl<A: Adapter, T: Clone + Send + Sync + 'static> FromConnectParts<A> for State<T> {
type Error = StateNotFound<T>;
fn from_connect_parts(s: &Arc<Socket<A>>, _: &Option<Value>) -> Result<Self, StateNotFound<T>> {
s.get_io()
.get_state::<T>()
.map(State)
.ok_or(StateNotFound(std::marker::PhantomData))
}
}
impl<A: Adapter, T: Clone + Send + Sync + 'static> FromDisconnectParts<A> for State<T> {
type Error = StateNotFound<T>;
fn from_disconnect_parts(
s: &Arc<Socket<A>>,
_: DisconnectReason,
) -> Result<Self, StateNotFound<T>> {
s.get_io()
.get_state::<T>()
.map(State)
.ok_or(StateNotFound(std::marker::PhantomData))
}
}
impl<A: Adapter, T: Clone + Send + Sync + 'static> FromMessageParts<A> for State<T> {
type Error = StateNotFound<T>;
fn from_message_parts(
s: &Arc<Socket<A>>,
_: &mut Value,
_: &Option<i64>,
) -> Result<Self, StateNotFound<T>> {
s.get_io()
.get_state::<T>()
.map(State)
.ok_or(StateNotFound(std::marker::PhantomData))
}
}
super::__impl_deref!(State);