mod expects;
use core::fmt;
use core::ops::Range;
use core::task::Poll;
use futures_core::TryStream;
pub use expects::*;
use crate::stream::Positioned;
pub type PolledResult<O, I> =
Poll<Result<Status<O, <I as Positioned>::Locator>, <I as TryStream>::Error>>;
pub type ParseResult<O, I> =
Result<O, ParseError<<I as Positioned>::Locator, <I as TryStream>::Error>>;
#[derive(Clone, Debug, PartialEq, Eq)]
pub enum Status<O, L> {
Success(O, Option<Error<L>>),
Failure(Error<L>, bool),
}
#[derive(Clone, Debug, PartialEq, Eq)]
pub struct Error<L> {
pub expects: Expects,
pub position: Range<L>,
}
impl<L> Error<L> {
#[inline]
pub fn rewindable(&self, pos: &L) -> bool
where
L: PartialEq,
{
self.position.start == *pos
}
}
impl<L> fmt::Display for Error<L> {
#[inline]
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
write!(f, "expected {}.", self.expects)
}
}
#[cfg(feature = "std")]
#[cfg_attr(feature = "nightly", doc(cfg(feature = "std")))]
impl<L: fmt::Debug> std::error::Error for Error<L> {}
#[derive(Clone, Debug, PartialEq, Eq)]
pub enum ParseError<L, E> {
Parser(Error<L>),
Stream(E),
}
impl<L, E> From<E> for ParseError<L, E> {
#[inline]
fn from(error: E) -> Self {
Self::Stream(error)
}
}
impl<L, E> ParseError<L, ParseError<L, E>> {
pub fn flatten(self) -> ParseError<L, E> {
match self {
Self::Parser(err) | Self::Stream(ParseError::Parser(err)) => ParseError::Parser(err),
Self::Stream(ParseError::Stream(e)) => ParseError::Stream(e),
}
}
}
impl<L, E: fmt::Display> fmt::Display for ParseError<L, E> {
#[inline]
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
match self {
Self::Parser(err) => err.fmt(f),
Self::Stream(e) => e.fmt(f),
}
}
}
#[cfg(feature = "std")]
#[cfg_attr(feature = "nightly", doc(cfg(feature = "std")))]
impl<L, E> std::error::Error for ParseError<L, E>
where
L: fmt::Debug + 'static,
E: std::error::Error + 'static,
{
#[inline]
fn source(&self) -> Option<&(dyn std::error::Error + 'static)> {
match self {
Self::Parser(e) => Some(e),
Self::Stream(e) => Some(e),
}
}
}