use core::fmt;
use std::any::Any;
use futures::Stream;
use crate::{async_iter::AsyncIterator, Error, Iter, StreamIter};
pub trait Message: Any + fmt::Debug + Clone + Send + Sync + Unpin {}
pub trait ErrorMessage: Any + fmt::Debug + fmt::Display + Send + Sync + Unpin {}
pub trait IntoMessages<M: Message, E: ErrorMessage> {
fn into_messages(self) -> impl AsyncIterator<Item = Result<M, E>>;
}
pub struct AsyncIter<I: AsyncIterator>(I);
pub fn async_iter<I: AsyncIterator>(i: I) -> AsyncIter<I> {
AsyncIter(i)
}
impl Message for () {}
impl ErrorMessage for anyhow::Error {}
#[derive(Debug, Clone, PartialEq, Eq)]
pub(crate) struct Msg<M: Message> {
pub(crate) inner: Option<Result<M, Error>>,
pub(crate) index: u64,
pub(crate) stream_id: u32,
}
impl<M: Message, E: ErrorMessage, S: Stream<Item = Result<M, E>> + Send> IntoMessages<M, E>
for StreamIter<S>
{
fn into_messages(self) -> impl AsyncIterator<Item = Result<M, E>> {
self
}
}
impl<E: ErrorMessage, I: Iterator + Send + Unpin> IntoMessages<I::Item, E> for Iter<I>
where
I::Item: Message,
{
fn into_messages(self) -> impl AsyncIterator<Item = Result<I::Item, E>> {
self.map(Ok)
}
}
impl<M: Message, E: ErrorMessage, I: AsyncIterator<Item = Result<M, E>>> IntoMessages<M, E>
for AsyncIter<I>
{
fn into_messages(self) -> impl AsyncIterator<Item = Result<M, E>> {
self.0
}
}
impl<E: ErrorMessage> IntoMessages<(), E> for () {
fn into_messages(self) -> impl AsyncIterator<Item = Result<(), E>> {
crate::empty()
}
}
impl<const N: usize, M: Message, E: ErrorMessage> IntoMessages<M, E> for [M; N] {
fn into_messages(self) -> impl AsyncIterator<Item = Result<M, E>> {
crate::iter(self.into_iter().map(Ok))
}
}
impl<M: Message, E: ErrorMessage> IntoMessages<M, E> for Vec<M> {
fn into_messages(self) -> impl AsyncIterator<Item = Result<M, E>> {
crate::iter(self.into_iter().map(Ok))
}
}
impl<M: Message, E: ErrorMessage> IntoMessages<M, E> for Option<M> {
fn into_messages(self) -> impl AsyncIterator<Item = Result<M, E>> {
crate::iter(self.into_iter().map(Ok))
}
}