Struct Partial

struct Partial<I> { ... }

Mark the input as a partial buffer for streaming input.

Complete input means that we already have all of the data. This will be the common case with small files that can be read entirely to memory.

In contrast, streaming input assumes that we might not have all of the data. This can happen with some network protocol or large file parsers, where the input buffer can be full and need to be resized or refilled.

See also StreamIsPartial to tell whether the input supports complete or partial parsing.

See also [Special Topics: Parsing Partial Input][crate::_topic::partial].

Example

Here is how it works in practice:

# use winnow::{Result, error::ErrMode, error::Needed, error::ContextError, token, ascii, stream::Partial};
# use winnow::prelude::*;

fn take_partial<'s>(i: &mut Partial<&'s [u8]>) -> ModalResult<&'s [u8], ContextError> {
  token::take(4u8).parse_next(i)
}

fn take_complete<'s>(i: &mut &'s [u8]) -> ModalResult<&'s [u8], ContextError> {
  token::take(4u8).parse_next(i)
}

// both parsers will take 4 bytes as expected
assert_eq!(take_partial.parse_peek(Partial::new(&b"abcde"[..])), Ok((Partial::new(&b"e"[..]), &b"abcd"[..])));
assert_eq!(take_complete.parse_peek(&b"abcde"[..]), Ok((&b"e"[..], &b"abcd"[..])));

// if the input is smaller than 4 bytes, the partial parser
// will return `Incomplete` to indicate that we need more data
assert_eq!(take_partial.parse_peek(Partial::new(&b"abc"[..])), Err(ErrMode::Incomplete(Needed::new(1))));

// but the complete parser will return an error
assert!(take_complete.parse_peek(&b"abc"[..]).is_err());

// the alpha0 function takes 0 or more alphabetic characters
fn alpha0_partial<'s>(i: &mut Partial<&'s str>) -> ModalResult<&'s str, ContextError> {
  ascii::alpha0.parse_next(i)
}

fn alpha0_complete<'s>(i: &mut &'s str) -> ModalResult<&'s str, ContextError> {
  ascii::alpha0.parse_next(i)
}

// if there's a clear limit to the taken characters, both parsers work the same way
assert_eq!(alpha0_partial.parse_peek(Partial::new("abcd;")), Ok((Partial::new(";"), "abcd")));
assert_eq!(alpha0_complete.parse_peek("abcd;"), Ok((";", "abcd")));

// but when there's no limit, the partial version returns `Incomplete`, because it cannot
// know if more input data should be taken. The whole input could be "abcd;", or
// "abcde;"
assert_eq!(alpha0_partial.parse_peek(Partial::new("abcd")), Err(ErrMode::Incomplete(Needed::new(1))));

// while the complete version knows that all of the data is there
assert_eq!(alpha0_complete.parse_peek("abcd"), Ok(("", "abcd")));

Implementations

impl<I> Partial<I>

fn new(input: I) -> Self

Create a partial input

fn into_inner(self: Self) -> I

Extract the original Stream

impl<I> AsBStr for Partial<I>

fn as_bstr(self: &Self) -> &[u8]

impl<I> AsBytes for Partial<I>

fn as_bytes(self: &Self) -> &[u8]

impl<I> Default for Partial<I>

fn default() -> Self

impl<I> Deref for Partial<I>

fn deref(self: &Self) -> &<Self as >::Target

impl<I> Freeze for Partial<I>

impl<I> Location for Partial<I>

fn previous_token_end(self: &Self) -> usize
fn current_token_start(self: &Self) -> usize

impl<I> Offset for Partial<I>

fn offset_from(self: &Self, other: &<Partial<I> as Stream>::Checkpoint) -> usize

impl<I> Offset for Partial<I>

fn offset_from(self: &Self, start: &Self) -> usize

impl<I> RefUnwindSafe for Partial<I>

impl<I> Send for Partial<I>

impl<I> SliceLen for Partial<I>

fn slice_len(self: &Self) -> usize

impl<I> StreamIsPartial for Partial<I>

fn complete(self: &mut Self) -> <Self as >::PartialState
fn restore_partial(self: &mut Self, state: <Self as >::PartialState)
fn is_partial_supported() -> bool
fn is_partial(self: &Self) -> bool

impl<I> StructuralPartialEq for Partial<I>

impl<I> Sync for Partial<I>

impl<I> Unpin for Partial<I>

impl<I> UnsafeUnpin for Partial<I>

impl<I> UnwindSafe for Partial<I>

impl<I> UpdateSlice for Partial<I>

fn update_slice(self: Self, inner: <Self as >::Slice) -> Self

impl<I, T> Compare for Partial<I>

fn compare(self: &Self, t: T) -> CompareResult

impl<I, T> FindSlice for Partial<I>

fn find_slice(self: &Self, substr: T) -> Option<Range<usize>>

impl<I: $crate::clone::Clone> Clone for Partial<I>

fn clone(self: &Self) -> Partial<I>

impl<I: $crate::cmp::Eq> Eq for Partial<I>

impl<I: $crate::cmp::Ord> Ord for Partial<I>

fn cmp(self: &Self, other: &Partial<I>) -> Ordering

impl<I: $crate::cmp::PartialEq> PartialEq for Partial<I>

fn eq(self: &Self, other: &Partial<I>) -> bool

impl<I: $crate::cmp::PartialOrd> PartialOrd for Partial<I>

fn partial_cmp(self: &Self, other: &Partial<I>) -> Option<Ordering>

impl<I: $crate::fmt::Debug> Debug for Partial<I>

fn fmt(self: &Self, f: &mut Formatter<'_>) -> Result

impl<I: $crate::marker::Copy> Copy for Partial<I>

impl<I: Stream> Stream for Partial<I>

fn iter_offsets(self: &Self) -> <Self as >::IterOffsets
fn eof_offset(self: &Self) -> usize
fn next_token(self: &mut Self) -> Option<<Self as >::Token>
fn peek_token(self: &Self) -> Option<<Self as >::Token>
fn offset_for<P>(self: &Self, predicate: P) -> Option<usize>
where
    P: Fn(<Self as >::Token) -> bool
fn offset_at(self: &Self, tokens: usize) -> Result<usize, Needed>
fn next_slice(self: &mut Self, offset: usize) -> <Self as >::Slice
unsafe fn next_slice_unchecked(self: &mut Self, offset: usize) -> <Self as >::Slice
fn peek_slice(self: &Self, offset: usize) -> <Self as >::Slice
unsafe fn peek_slice_unchecked(self: &Self, offset: usize) -> <Self as >::Slice
fn checkpoint(self: &Self) -> <Self as >::Checkpoint
fn reset(self: &mut Self, checkpoint: &<Self as >::Checkpoint)
fn raw(self: &Self) -> &dyn Debug

impl<I: crate::lib::std::fmt::Display> Display for Partial<I>

fn fmt(self: &Self, f: &mut Formatter<'_>) -> Result

impl<P, T> Receiver for Partial<I>

impl<T> Any for Partial<I>

fn type_id(self: &Self) -> TypeId

impl<T> Borrow for Partial<I>

fn borrow(self: &Self) -> &T

impl<T> BorrowMut for Partial<I>

fn borrow_mut(self: &mut Self) -> &mut T

impl<T> CloneToUninit for Partial<I>

unsafe fn clone_to_uninit(self: &Self, dest: *mut u8)

impl<T> From for Partial<I>

fn from(t: T) -> T

Returns the argument unchanged.

impl<T, U> Into for Partial<I>

fn into(self: Self) -> U

Calls U::from(self).

That is, this conversion is whatever the implementation of [From]<T> for U chooses to do.

impl<T, U> TryFrom for Partial<I>

fn try_from(value: U) -> Result<T, <T as TryFrom<U>>::Error>

impl<T, U> TryInto for Partial<I>

fn try_into(self: Self) -> Result<U, <U as TryFrom<T>>::Error>