use std::any::Any;
use std::fmt;
use crate::error::CodecError;
#[derive(Clone, Copy, Debug, Eq, Hash, PartialEq)]
pub struct WireTypeId(&'static str);
impl WireTypeId {
#[must_use]
pub const fn new(s: &'static str) -> Self {
Self(s)
}
#[must_use]
pub const fn as_str(self) -> &'static str {
self.0
}
}
impl fmt::Display for WireTypeId {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
f.write_str(self.0)
}
}
pub trait WireValue: fmt::Debug + Send + Sync + 'static {
fn wire_type_id() -> WireTypeId
where
Self: Sized;
}
pub trait ErasedWireValue: fmt::Debug + Send + Sync + 'static {
fn type_id(&self) -> WireTypeId;
fn as_any(&self) -> &dyn Any;
}
impl<T> ErasedWireValue for T
where
T: WireValue,
{
fn type_id(&self) -> WireTypeId {
<T as WireValue>::wire_type_id()
}
fn as_any(&self) -> &dyn Any {
self
}
}
pub trait WireCodec: Send + Sync + 'static {
fn content_type(&self) -> &'static str;
fn encode(&self, value: &dyn ErasedWireValue) -> Result<Vec<u8>, CodecError>;
fn decode(
&self,
type_id: WireTypeId,
bytes: &[u8],
) -> Result<Box<dyn ErasedWireValue>, CodecError>;
}