Skip to main content

winnow/
parser.rs

1//! Basic types to build the parsers
2
3use crate::combinator::impls;
4#[cfg(feature = "unstable-recover")]
5#[cfg(feature = "std")]
6use crate::error::FromRecoverableError;
7use crate::error::{AddContext, FromExternalError, ParseError, ParserError, Result};
8use crate::stream::{Compare, Location, ParseSlice, Stream, StreamIsPartial};
9#[cfg(feature = "unstable-recover")]
10#[cfg(feature = "std")]
11use crate::stream::{Recover, Recoverable};
12
13/// Core trait for parsing
14///
15/// The simplest way to implement a `Parser` is with a function
16/// ```rust
17/// use winnow::prelude::*;
18///
19/// fn empty(input: &mut &str) -> ModalResult<()> {
20///     let output = ();
21///     Ok(output)
22/// }
23///
24/// let (input, output) = empty.parse_peek("Hello").unwrap();
25/// assert_eq!(input, "Hello");  // We didn't consume any input
26/// ```
27///
28/// which can be made stateful by returning a function
29/// ```rust
30/// use winnow::prelude::*;
31///
32/// fn empty<O: Clone>(output: O) -> impl FnMut(&mut &str) -> ModalResult<O> {
33///     move |input: &mut &str| {
34///         let output = output.clone();
35///         Ok(output)
36///     }
37/// }
38///
39/// let (input, output) = empty("World").parse_peek("Hello").unwrap();
40/// assert_eq!(input, "Hello");  // We didn't consume any input
41/// assert_eq!(output, "World");
42/// ```
43///
44/// Additionally, some basic types implement `Parser` as well, including
45/// - `u8` and `char`, see [`winnow::token::one_of`][crate::token::one_of]
46/// - `&[u8]` and `&str`, see [`winnow::token::literal`][crate::token::literal]
47pub trait Parser<I, O, E> {
48    /// Parse all of `input`, generating `O` from it
49    ///
50    /// This is intended for integrating your parser into the rest of your application.
51    ///
52    /// For one [`Parser`] to drive another [`Parser`] forward or for
53    /// [incremental parsing][StreamIsPartial], see instead [`Parser::parse_next`].
54    ///
55    /// This assumes the [`Parser`] intends to read all of `input` and will return an
56    /// [`eof`][crate::combinator::eof] error if it does not.
57    /// To ignore trailing `input`, combine your parser with a [`rest`][crate::token::rest]
58    /// (e.g. `(parser, rest).parse(input)`).
59    ///
60    /// See also the [tutorial][crate::_tutorial::chapter_6].
61    #[inline]
62    fn parse(&mut self, mut input: I) -> Result<O, ParseError<I, <E as ParserError<I>>::Inner>>
63    where
64        Self: core::marker::Sized,
65        I: Stream,
66        // Force users to deal with `Incomplete` when `StreamIsPartial<true>`
67        I: StreamIsPartial,
68        E: ParserError<I>,
69        <E as ParserError<I>>::Inner: ParserError<I>,
70    {
71        debug_assert!(
72            !I::is_partial_supported(),
73            "partial streams need to handle `ErrMode::Incomplete`"
74        );
75
76        let start = input.checkpoint();
77        let (o, _) = (self.by_ref(), crate::combinator::eof)
78            .parse_next(&mut input)
79            .map_err(|e| {
80                let e = e.into_inner().unwrap_or_else(|_err| {
81                    panic!("complete parsers should not report `ErrMode::Incomplete(_)`")
82                });
83                ParseError::new(input, start, e)
84            })?;
85        Ok(o)
86    }
87
88    /// Repeat this parse until all of `input` is consumed, generating `O` from it
89    ///
90    /// This is intended for integrating your parser into the rest of your application.
91    /// To instead iterate inside of a parser, see [iterator][crate::combinator::iterator].
92    ///
93    /// This assumes the [`Parser`] intends to read all of `input` and will return an
94    /// [`eof`][crate::combinator::eof] error if it does not.
95    ///
96    /// # Example
97    ///
98    /// ```rust
99    /// # #[cfg(feature = "ascii")] {
100    /// # use winnow::ascii::dec_uint;
101    /// # use winnow::ascii::newline;
102    /// # use winnow::combinator::terminated;
103    /// # use winnow::combinator::opt;
104    /// # use winnow::prelude::*;
105    /// fn number(input: &mut &str) -> Result<u32, ()> {
106    ///   terminated(dec_uint, opt(newline)).parse_next(input)
107    /// }
108    ///
109    /// let input = "10\n20\n30";
110    /// let numbers = number.parse_iter(input)
111    ///     .map(|r| r.unwrap()).collect::<Vec<_>>();
112    /// assert_eq!(numbers, vec![10, 20, 30]);
113    /// # }
114    /// ```
115    #[inline]
116    fn parse_iter(&mut self, input: I) -> impls::ParseIter<'_, Self, I, O, E>
117    where
118        Self: core::marker::Sized,
119        I: Stream,
120        // Force users to deal with `Incomplete` when `StreamIsPartial<true>`
121        I: StreamIsPartial,
122        E: ParserError<I>,
123        <E as ParserError<I>>::Inner: ParserError<I>,
124    {
125        debug_assert!(
126            !I::is_partial_supported(),
127            "partial streams need to handle `ErrMode::Incomplete`"
128        );
129
130        let start = input.checkpoint();
131        impls::ParseIter {
132            parser: self,
133            input: Some(input),
134            start: Some(start),
135            marker: Default::default(),
136        }
137    }
138
139    /// Take tokens from the [`Stream`], turning it into the output
140    ///
141    /// This includes advancing the input [`Stream`] to the next location.
142    ///
143    /// On error, `input` will be left pointing at the error location.
144    ///
145    /// This is intended for a [`Parser`] to drive another [`Parser`] forward or for
146    /// [incremental parsing][StreamIsPartial]
147    fn parse_next(&mut self, input: &mut I) -> Result<O, E>;
148
149    /// Take tokens from the [`Stream`], turning it into the output
150    ///
151    /// This returns a copy of the [`Stream`] advanced to the next location.
152    ///
153    /// <div class="warning">
154    ///
155    /// Generally, prefer [`Parser::parse_next`].
156    /// This is primarily intended for:
157    /// - Migrating from older versions / `nom`
158    /// - Testing [`Parser`]s
159    ///
160    /// For look-ahead parsing, see instead [`peek`][crate::combinator::peek].
161    ///
162    /// </div>
163    #[inline(always)]
164    fn parse_peek(&mut self, mut input: I) -> Result<(I, O), E> {
165        match self.parse_next(&mut input) {
166            Ok(o) => Ok((input, o)),
167            Err(err) => Err(err),
168        }
169    }
170
171    /// Treat `&mut Self` as a parser
172    ///
173    /// This helps when needing to move a `Parser` when all you have is a `&mut Parser`.
174    ///
175    /// # Example
176    ///
177    /// Because parsers are `FnMut`, they can be called multiple times. This prevents moving `f`
178    /// into [`length_take`][crate::binary::length_take] and `g` into
179    /// [`Parser::complete_err`]:
180    /// ```rust,compile_fail
181    /// # use winnow::prelude::*;
182    /// # use winnow::Parser;
183    /// # use winnow::error::ParserError;
184    /// # use winnow::binary::length_take;
185    /// pub fn length_value<'i, O, E: ParserError<&'i [u8]>>(
186    ///     mut f: impl Parser<&'i [u8], usize, E>,
187    ///     mut g: impl Parser<&'i [u8], O, E>
188    /// ) -> impl Parser<&'i [u8], O, E> {
189    ///   move |i: &mut &'i [u8]| {
190    ///     let mut data = length_take(f).parse_next(i)?;
191    ///     let o = g.complete_err().parse_next(&mut data)?;
192    ///     Ok(o)
193    ///   }
194    /// }
195    /// ```
196    ///
197    /// By adding `by_ref`, we can make this work:
198    /// ```rust
199    /// # #[cfg(feature = "binary")] {
200    /// # use winnow::prelude::*;
201    /// # use winnow::Parser;
202    /// # use winnow::error::ParserError;
203    /// # use winnow::binary::length_take;
204    /// pub fn length_value<'i, O, E: ParserError<&'i [u8]>>(
205    ///     mut f: impl Parser<&'i [u8], usize, E>,
206    ///     mut g: impl Parser<&'i [u8], O, E>
207    /// ) -> impl Parser<&'i [u8], O, E> {
208    ///   move |i: &mut &'i [u8]| {
209    ///     let mut data = length_take(f.by_ref()).parse_next(i)?;
210    ///     let o = g.by_ref().complete_err().parse_next(&mut data)?;
211    ///     Ok(o)
212    ///   }
213    /// }
214    /// # }
215    /// ```
216    #[inline(always)]
217    fn by_ref(&mut self) -> impls::ByRef<'_, Self, I, O, E>
218    where
219        Self: core::marker::Sized,
220    {
221        impls::ByRef {
222            p: self,
223            marker: Default::default(),
224        }
225    }
226
227    /// Produce the provided value
228    ///
229    /// # Example
230    ///
231    /// ```rust
232    /// # #[cfg(feature = "ascii")] {
233    /// # use winnow::{error::ErrMode, Parser};
234    /// # use winnow::prelude::*;
235    /// use winnow::ascii::alpha1;
236    ///
237    /// fn parser<'i>(input: &mut &'i str) -> ModalResult<i32> {
238    ///     alpha1.value(1234).parse_next(input)
239    /// }
240    ///
241    /// assert_eq!(parser.parse_peek("abcd"), Ok(("", 1234)));
242    /// assert!(parser.parse_peek("123abcd;").is_err());
243    /// # }
244    /// ```
245    #[doc(alias = "to")]
246    #[inline(always)]
247    fn value<O2>(self, val: O2) -> impls::Value<Self, I, O, O2, E>
248    where
249        Self: core::marker::Sized,
250        O2: Clone,
251    {
252        impls::Value {
253            parser: self,
254            val,
255            marker: Default::default(),
256        }
257    }
258
259    /// Produce a type's default value
260    ///
261    /// # Example
262    ///
263    /// ```rust
264    /// # #[cfg(feature = "ascii")] {
265    /// # use winnow::{error::ErrMode, Parser};
266    /// # use winnow::prelude::*;
267    /// use winnow::ascii::alpha1;
268    ///
269    /// fn parser<'i>(input: &mut &'i str) -> ModalResult<u32> {
270    ///     alpha1.default_value().parse_next(input)
271    /// }
272    ///
273    /// assert_eq!(parser.parse_peek("abcd"), Ok(("", 0)));
274    /// assert!(parser.parse_peek("123abcd;").is_err());
275    /// # }
276    /// ```
277    #[inline(always)]
278    fn default_value<O2>(self) -> impls::DefaultValue<Self, I, O, O2, E>
279    where
280        Self: core::marker::Sized,
281        O2: core::default::Default,
282    {
283        impls::DefaultValue {
284            parser: self,
285            marker: Default::default(),
286        }
287    }
288
289    /// Discards the output of the `Parser`
290    ///
291    /// # Example
292    ///
293    /// ```rust
294    /// # #[cfg(feature = "ascii")] {
295    /// # use winnow::{error::ErrMode, Parser};
296    /// # use winnow::prelude::*;
297    /// use winnow::ascii::alpha1;
298    ///
299    /// fn parser<'i>(input: &mut &'i str) -> ModalResult<()> {
300    ///     alpha1.void().parse_next(input)
301    /// }
302    ///
303    /// assert_eq!(parser.parse_peek("abcd"), Ok(("", ())));
304    /// assert!(parser.parse_peek("123abcd;").is_err());
305    /// # }
306    /// ```
307    #[inline(always)]
308    fn void(self) -> impls::Void<Self, I, O, E>
309    where
310        Self: core::marker::Sized,
311    {
312        impls::Void {
313            parser: self,
314            marker: Default::default(),
315        }
316    }
317
318    /// Convert the parser's output to another type using [`std::convert::From`]
319    ///
320    /// # Example
321    ///
322    /// ```rust
323    /// # #[cfg(feature = "ascii")] {
324    /// # use winnow::prelude::*;
325    /// # use winnow::error::ContextError;
326    /// use winnow::ascii::alpha1;
327    ///
328    /// fn parser1<'s>(i: &mut &'s str) -> ModalResult<&'s str> {
329    ///   alpha1(i)
330    /// }
331    ///
332    /// let mut parser2 = parser1.output_into();
333    ///
334    /// // the parser converts the &str output of the child parser into a Vec<u8>
335    /// let bytes: ModalResult<(_, Vec<u8>), _> = parser2.parse_peek("abcd");
336    /// assert_eq!(bytes, Ok(("", vec![97, 98, 99, 100])));
337    /// # }
338    /// ```
339    #[inline(always)]
340    fn output_into<O2>(self) -> impls::OutputInto<Self, I, O, O2, E>
341    where
342        Self: core::marker::Sized,
343        O: Into<O2>,
344    {
345        impls::OutputInto {
346            parser: self,
347            marker: Default::default(),
348        }
349    }
350
351    /// Produce the consumed input as produced value.
352    ///
353    /// # Example
354    ///
355    /// ```rust
356    /// # #[cfg(feature = "ascii")] {
357    /// # use winnow::{error::ErrMode, Parser};
358    /// # use winnow::prelude::*;
359    /// use winnow::ascii::{alpha1};
360    /// use winnow::combinator::separated_pair;
361    ///
362    /// fn parser<'i>(input: &mut &'i str) -> ModalResult<&'i str> {
363    ///     separated_pair(alpha1, ',', alpha1).take().parse_next(input)
364    /// }
365    ///
366    /// assert_eq!(parser.parse_peek("abcd,efgh"), Ok(("", "abcd,efgh")));
367    /// assert!(parser.parse_peek("abcd;").is_err());
368    /// # }
369    /// ```
370    #[doc(alias = "concat")]
371    #[doc(alias = "recognize")]
372    #[inline(always)]
373    fn take(self) -> impls::Take<Self, I, O, E>
374    where
375        Self: core::marker::Sized,
376        I: Stream,
377    {
378        impls::Take {
379            parser: self,
380            marker: Default::default(),
381        }
382    }
383
384    /// Produce the consumed input with the output
385    ///
386    /// Functions similarly to [take][Parser::take] except it
387    /// returns the parser output as well.
388    ///
389    /// This can be useful especially in cases where the output is not the same type
390    /// as the input, or the input is a user defined type.
391    ///
392    /// Returned tuple is of the format `(produced output, consumed input)`.
393    ///
394    /// # Example
395    ///
396    /// ```rust
397    /// # #[cfg(feature = "ascii")] {
398    /// # use winnow::prelude::*;
399    /// # use winnow::{error::ErrMode};
400    /// use winnow::ascii::{alpha1};
401    /// use winnow::token::literal;
402    /// use winnow::combinator::separated_pair;
403    ///
404    /// fn parser<'i>(input: &mut &'i str) -> ModalResult<(bool, &'i str)> {
405    ///     separated_pair(alpha1, ',', alpha1).value(true).with_taken().parse_next(input)
406    /// }
407    ///
408    /// assert_eq!(parser.parse_peek("abcd,efgh1"), Ok(("1", (true, "abcd,efgh"))));
409    /// assert!(parser.parse_peek("abcd;").is_err());
410    /// # }
411    /// ```
412    #[doc(alias = "consumed")]
413    #[doc(alias = "with_recognized")]
414    #[inline(always)]
415    fn with_taken(self) -> impls::WithTaken<Self, I, O, E>
416    where
417        Self: core::marker::Sized,
418        I: Stream,
419    {
420        impls::WithTaken {
421            parser: self,
422            marker: Default::default(),
423        }
424    }
425
426    /// Produce the location of the consumed input as produced value.
427    ///
428    /// # Example
429    ///
430    /// ```rust
431    /// # #[cfg(feature = "ascii")] {
432    /// # use winnow::prelude::*;
433    /// # use winnow::{error::ErrMode, stream::Stream};
434    /// # use std::ops::Range;
435    /// use winnow::stream::LocatingSlice;
436    /// use winnow::ascii::alpha1;
437    /// use winnow::combinator::separated_pair;
438    ///
439    /// fn parser<'i>(input: &mut LocatingSlice<&'i str>) -> ModalResult<(Range<usize>, Range<usize>)> {
440    ///     separated_pair(alpha1.span(), ',', alpha1.span()).parse_next(input)
441    /// }
442    ///
443    /// assert_eq!(parser.parse(LocatingSlice::new("abcd,efgh")), Ok((0..4, 5..9)));
444    /// assert!(parser.parse_peek(LocatingSlice::new("abcd;")).is_err());
445    /// # }
446    /// ```
447    #[inline(always)]
448    fn span(self) -> impls::Span<Self, I, O, E>
449    where
450        Self: core::marker::Sized,
451        I: Stream + Location,
452    {
453        impls::Span {
454            parser: self,
455            marker: Default::default(),
456        }
457    }
458
459    /// Produce the location of consumed input with the output
460    ///
461    /// Functions similarly to [`Parser::span`] except it
462    /// returns the parser output as well.
463    ///
464    /// This can be useful especially in cases where the output is not the same type
465    /// as the input, or the input is a user defined type.
466    ///
467    /// Returned tuple is of the format `(produced output, consumed input)`.
468    ///
469    /// # Example
470    ///
471    /// ```rust
472    /// # #[cfg(feature = "ascii")] {
473    /// # use winnow::prelude::*;
474    /// # use winnow::{error::ErrMode, stream::Stream};
475    /// # use std::ops::Range;
476    /// use winnow::stream::LocatingSlice;
477    /// use winnow::ascii::alpha1;
478    /// use winnow::token::literal;
479    /// use winnow::combinator::separated_pair;
480    ///
481    /// fn parser<'i>(input: &mut LocatingSlice<&'i str>) -> ModalResult<((usize, Range<usize>), (usize, Range<usize>))> {
482    ///     separated_pair(alpha1.value(1).with_span(), ',', alpha1.value(2).with_span()).parse_next(input)
483    /// }
484    ///
485    /// assert_eq!(parser.parse(LocatingSlice::new("abcd,efgh")), Ok(((1, 0..4), (2, 5..9))));
486    /// assert!(parser.parse_peek(LocatingSlice::new("abcd;")).is_err());
487    /// # }
488    /// ```
489    #[inline(always)]
490    fn with_span(self) -> impls::WithSpan<Self, I, O, E>
491    where
492        Self: core::marker::Sized,
493        I: Stream + Location,
494    {
495        impls::WithSpan {
496            parser: self,
497            marker: Default::default(),
498        }
499    }
500
501    /// Maps a function over the output of a parser
502    ///
503    /// # Example
504    ///
505    /// ```rust
506    /// # #[cfg(feature = "ascii")] {
507    /// # use winnow::prelude::*;
508    /// # use winnow::{error::ErrMode, Parser};
509    /// # use winnow::ascii::digit1;
510    ///
511    /// fn parser<'i>(input: &mut &'i str) -> ModalResult<usize> {
512    ///     digit1.map(|s: &str| s.len()).parse_next(input)
513    /// }
514    ///
515    /// // the parser will count how many characters were returned by digit1
516    /// assert_eq!(parser.parse_peek("123456"), Ok(("", 6)));
517    ///
518    /// // this will fail if digit1 fails
519    /// assert!(parser.parse_peek("abc").is_err());
520    /// # }
521    /// ```
522    #[inline(always)]
523    fn map<G, O2>(self, map: G) -> impls::Map<Self, G, I, O, O2, E>
524    where
525        G: FnMut(O) -> O2,
526        Self: core::marker::Sized,
527    {
528        impls::Map {
529            parser: self,
530            map,
531            marker: Default::default(),
532        }
533    }
534
535    /// Applies a function returning a `Result` over the output of a parser.
536    ///
537    /// # Example
538    ///
539    /// ```rust
540    /// # #[cfg(feature = "ascii")] {
541    /// # use winnow::{error::ErrMode, Parser};
542    /// # use winnow::prelude::*;
543    /// use winnow::ascii::digit1;
544    ///
545    /// fn parser<'i>(input: &mut &'i str) -> ModalResult<u8> {
546    ///     digit1.try_map(|s: &str| s.parse::<u8>()).parse_next(input)
547    /// }
548    ///
549    /// // the parser will convert the result of digit1 to a number
550    /// assert_eq!(parser.parse_peek("123"), Ok(("", 123)));
551    ///
552    /// // this will fail if digit1 fails
553    /// assert!(parser.parse_peek("abc").is_err());
554    ///
555    /// // this will fail if the mapped function fails (a `u8` is too small to hold `123456`)
556    /// assert!(parser.parse_peek("123456").is_err());
557    /// # }
558    /// ```
559    #[inline(always)]
560    fn try_map<G, O2, E2>(self, map: G) -> impls::TryMap<Self, G, I, O, O2, E, E2>
561    where
562        Self: core::marker::Sized,
563        G: FnMut(O) -> Result<O2, E2>,
564        I: Stream,
565        E: FromExternalError<I, E2>,
566        E: ParserError<I>,
567    {
568        impls::TryMap {
569            parser: self,
570            map,
571            marker: Default::default(),
572        }
573    }
574
575    /// Apply both [`Parser::verify`] and [`Parser::map`].
576    ///
577    /// # Example
578    ///
579    /// ```rust
580    /// # #[cfg(feature = "ascii")] {
581    /// # use winnow::{error::ErrMode, Parser};
582    /// # use winnow::prelude::*;
583    /// use winnow::ascii::digit1;
584    ///
585    /// fn parser<'i>(input: &mut &'i str) -> ModalResult<u8> {
586    ///     digit1.verify_map(|s: &str| s.parse::<u8>().ok()).parse_next(input)
587    /// }
588    ///
589    /// // the parser will convert the result of digit1 to a number
590    /// assert_eq!(parser.parse_peek("123"), Ok(("", 123)));
591    ///
592    /// // this will fail if digit1 fails
593    /// assert!(parser.parse_peek("abc").is_err());
594    ///
595    /// // this will fail if the mapped function fails (a `u8` is too small to hold `123456`)
596    /// assert!(parser.parse_peek("123456").is_err());
597    /// # }
598    /// ```
599    #[doc(alias = "satisfy_map")]
600    #[doc(alias = "filter_map")]
601    #[doc(alias = "map_opt")]
602    #[inline(always)]
603    fn verify_map<G, O2>(self, map: G) -> impls::VerifyMap<Self, G, I, O, O2, E>
604    where
605        Self: core::marker::Sized,
606        G: FnMut(O) -> Option<O2>,
607        I: Stream,
608        E: ParserError<I>,
609    {
610        impls::VerifyMap {
611            parser: self,
612            map,
613            marker: Default::default(),
614        }
615    }
616
617    /// Creates a parser from the output of this one
618    ///
619    /// # Example
620    ///
621    /// ```rust
622    /// # #[cfg(feature = "binary")] {
623    /// # use winnow::{error::ErrMode, ModalResult, Parser};
624    /// use winnow::token::take;
625    /// use winnow::binary::u8;
626    ///
627    /// fn length_take<'s>(input: &mut &'s [u8]) -> ModalResult<&'s [u8]> {
628    ///     u8.flat_map(take).parse_next(input)
629    /// }
630    ///
631    /// assert_eq!(length_take.parse_peek(&[2, 0, 1, 2][..]), Ok((&[2][..], &[0, 1][..])));
632    /// assert!(length_take.parse_peek(&[4, 0, 1, 2][..]).is_err());
633    /// # }
634    /// ```
635    ///
636    /// which is the same as
637    /// ```rust
638    /// # #[cfg(feature = "binary")] {
639    /// # use winnow::{error::ErrMode, ModalResult, Parser};
640    /// use winnow::token::take;
641    /// use winnow::binary::u8;
642    ///
643    /// fn length_take<'s>(input: &mut &'s [u8]) -> ModalResult<&'s [u8]> {
644    ///     let length = u8.parse_next(input)?;
645    ///     let data = take(length).parse_next(input)?;
646    ///     Ok(data)
647    /// }
648    ///
649    /// assert_eq!(length_take.parse_peek(&[2, 0, 1, 2][..]), Ok((&[2][..], &[0, 1][..])));
650    /// assert!(length_take.parse_peek(&[4, 0, 1, 2][..]).is_err());
651    /// # }
652    /// ```
653    #[inline(always)]
654    fn flat_map<G, H, O2>(self, map: G) -> impls::FlatMap<Self, G, H, I, O, O2, E>
655    where
656        Self: core::marker::Sized,
657        G: FnMut(O) -> H,
658        H: Parser<I, O2, E>,
659    {
660        impls::FlatMap {
661            f: self,
662            g: map,
663            marker: Default::default(),
664        }
665    }
666
667    /// Applies a second parser over the output of the first one
668    ///
669    /// # Example
670    ///
671    /// ```rust
672    /// # #[cfg(feature = "ascii")] {
673    /// # use winnow::{error::ErrMode, Parser};
674    /// # use winnow::prelude::*;
675    /// use winnow::ascii::digit1;
676    /// use winnow::token::take;
677    ///
678    /// fn parser<'i>(input: &mut &'i str) -> ModalResult<&'i str> {
679    ///     take(5u8).and_then(digit1).parse_next(input)
680    /// }
681    ///
682    /// assert_eq!(parser.parse_peek("12345"), Ok(("", "12345")));
683    /// assert_eq!(parser.parse_peek("123ab"), Ok(("", "123")));
684    /// assert!(parser.parse_peek("123").is_err());
685    /// # }
686    /// ```
687    #[inline(always)]
688    fn and_then<G, O2>(self, inner: G) -> impls::AndThen<Self, G, I, O, O2, E>
689    where
690        Self: core::marker::Sized,
691        G: Parser<O, O2, E>,
692        O: StreamIsPartial,
693        I: Stream,
694    {
695        impls::AndThen {
696            outer: self,
697            inner,
698            marker: Default::default(),
699        }
700    }
701
702    /// Apply [`std::str::FromStr`] to the output of the parser
703    ///
704    /// # Example
705    ///
706    /// ```rust
707    /// # #[cfg(feature = "ascii")] {
708    /// # use winnow::prelude::*;
709    /// use winnow::{error::ErrMode, Parser};
710    /// use winnow::ascii::digit1;
711    ///
712    /// fn parser<'s>(input: &mut &'s str) -> ModalResult<u64> {
713    ///     digit1.parse_to().parse_next(input)
714    /// }
715    ///
716    /// // the parser will count how many characters were returned by digit1
717    /// assert_eq!(parser.parse_peek("123456"), Ok(("", 123456)));
718    ///
719    /// // this will fail if digit1 fails
720    /// assert!(parser.parse_peek("abc").is_err());
721    /// # }
722    /// ```
723    #[doc(alias = "from_str")]
724    #[inline(always)]
725    fn parse_to<O2>(self) -> impls::ParseTo<Self, I, O, O2, E>
726    where
727        Self: core::marker::Sized,
728        I: Stream,
729        O: ParseSlice<O2>,
730        E: ParserError<I>,
731    {
732        impls::ParseTo {
733            p: self,
734            marker: Default::default(),
735        }
736    }
737
738    /// Returns the output of the child parser if it satisfies a verification function.
739    ///
740    /// The verification function takes as argument a reference to the output of the
741    /// parser.
742    ///
743    /// # Example
744    ///
745    /// ```rust
746    /// # #[cfg(feature = "ascii")] {
747    /// # use winnow::{error::ErrMode, Parser};
748    /// # use winnow::ascii::alpha1;
749    /// # use winnow::prelude::*;
750    ///
751    /// fn parser<'i>(input: &mut &'i str) -> ModalResult<&'i str> {
752    ///     alpha1.verify(|s: &str| s.len() == 4).parse_next(input)
753    /// }
754    ///
755    /// assert_eq!(parser.parse_peek("abcd"), Ok(("", "abcd")));
756    /// assert!(parser.parse_peek("abcde").is_err());
757    /// assert!(parser.parse_peek("123abcd;").is_err());
758    /// # }
759    /// ```
760    #[doc(alias = "satisfy")]
761    #[doc(alias = "filter")]
762    #[inline(always)]
763    fn verify<G, O2>(self, filter: G) -> impls::Verify<Self, G, I, O, O2, E>
764    where
765        Self: core::marker::Sized,
766        G: FnMut(&O2) -> bool,
767        I: Stream,
768        O: core::borrow::Borrow<O2>,
769        O2: ?Sized,
770        E: ParserError<I>,
771    {
772        impls::Verify {
773            parser: self,
774            filter,
775            marker: Default::default(),
776        }
777    }
778
779    /// If parsing fails, add context to the error
780    ///
781    /// This is used mainly to add user friendly information
782    /// to errors when backtracking through a parse tree.
783    ///
784    /// See also [tutorial][crate::_tutorial::chapter_7].
785    ///
786    /// # Example
787    ///
788    /// ```rust
789    /// # #[cfg(feature = "ascii")] {
790    /// # use winnow::prelude::*;
791    /// # use winnow::{error::ErrMode, Parser};
792    /// # use winnow::ascii::digit1;
793    /// # use winnow::error::StrContext;
794    /// # use winnow::error::StrContextValue;
795    ///
796    /// fn parser<'i>(input: &mut &'i str) -> ModalResult<&'i str> {
797    ///     digit1
798    ///       .context(StrContext::Expected(StrContextValue::Description("digit")))
799    ///       .parse_next(input)
800    /// }
801    ///
802    /// assert_eq!(parser.parse_peek("123456"), Ok(("", "123456")));
803    /// assert!(parser.parse_peek("abc").is_err());
804    /// # }
805    /// ```
806    #[doc(alias = "labelled")]
807    #[inline(always)]
808    fn context<C>(self, context: C) -> impls::Context<Self, I, O, E, C>
809    where
810        Self: core::marker::Sized,
811        I: Stream,
812        E: AddContext<I, C>,
813        E: ParserError<I>,
814        C: Clone + core::fmt::Debug,
815    {
816        impls::Context {
817            parser: self,
818            context,
819            marker: Default::default(),
820        }
821    }
822
823    /// If parsing fails, dynamically add context to the error
824    ///
825    /// This is used mainly to add user friendly information
826    /// to errors when backtracking through a parse tree.
827    ///
828    /// See also [tutorial][crate::_tutorial::chapter_7].
829    ///
830    /// # Example
831    ///
832    /// ```rust
833    /// # #[cfg(feature = "ascii")] {
834    /// # use winnow::prelude::*;
835    /// # use winnow::{error::ErrMode, Parser};
836    /// # use winnow::ascii::digit1;
837    /// # use winnow::error::StrContext;
838    /// # use winnow::error::StrContextValue;
839    ///
840    /// fn parser<'i>(input: &mut &'i str) -> ModalResult<&'i str> {
841    ///     digit1
842    ///       .context_with(|| {
843    ///         "0123456789".chars().map(|c| StrContext::Expected(c.into()))
844    ///       })
845    ///       .parse_next(input)
846    /// }
847    ///
848    /// assert_eq!(parser.parse_peek("123456"), Ok(("", "123456")));
849    /// assert!(parser.parse_peek("abc").is_err());
850    /// # }
851    /// ```
852    #[doc(alias = "labelled")]
853    #[inline(always)]
854    fn context_with<F, C, FI>(self, context: F) -> impls::ContextWith<Self, I, O, E, F, C, FI>
855    where
856        Self: core::marker::Sized,
857        I: Stream,
858        E: AddContext<I, C>,
859        E: ParserError<I>,
860        F: Fn() -> FI + Clone,
861        C: core::fmt::Debug,
862        FI: Iterator<Item = C>,
863    {
864        impls::ContextWith {
865            parser: self,
866            context,
867            marker: Default::default(),
868        }
869    }
870
871    /// Maps a function over the error of a parser
872    ///
873    /// # Example
874    ///
875    /// ```rust
876    /// # #[cfg(feature = "ascii")] {
877    /// # use winnow::prelude::*;
878    /// # use winnow::Parser;
879    /// # use winnow::Result;
880    /// # use winnow::ascii::digit1;
881    /// # use winnow::error::StrContext;
882    /// # use winnow::error::AddContext;
883    /// # use winnow::error::ContextError;
884    ///
885    /// fn parser<'i>(input: &mut &'i str) -> Result<&'i str> {
886    ///     digit1.map_err(|mut e: ContextError| {
887    ///         e.extend("0123456789".chars().map(|c| StrContext::Expected(c.into())));
888    ///         e
889    ///     }).parse_next(input)
890    /// }
891    ///
892    /// assert_eq!(parser.parse_peek("123456"), Ok(("", "123456")));
893    /// assert!(parser.parse_peek("abc").is_err());
894    /// # }
895    /// ```
896    #[inline(always)]
897    fn map_err<G, E2>(self, map: G) -> impls::MapErr<Self, G, I, O, E, E2>
898    where
899        G: FnMut(E) -> E2,
900        Self: core::marker::Sized,
901    {
902        impls::MapErr {
903            parser: self,
904            map,
905            marker: Default::default(),
906        }
907    }
908
909    /// Transforms [`Incomplete`][crate::error::ErrMode::Incomplete] into [`Backtrack`][crate::error::ErrMode::Backtrack]
910    ///
911    /// # Example
912    ///
913    /// ```rust
914    /// # use winnow::{error::ErrMode, error::InputError, stream::Partial, Parser};
915    /// # use winnow::token::take;
916    /// # use winnow::prelude::*;
917    /// # fn main() {
918    ///
919    /// fn parser<'i>(input: &mut Partial<&'i str>) -> ModalResult<&'i str, InputError<Partial<&'i str>>> {
920    ///     take(5u8).complete_err().parse_next(input)
921    /// }
922    ///
923    /// assert_eq!(parser.parse_peek(Partial::new("abcdefg")), Ok((Partial::new("fg"), "abcde")));
924    /// assert_eq!(parser.parse_peek(Partial::new("abcd")), Err(ErrMode::Backtrack(InputError::at(Partial::new("abcd")))));
925    /// # }
926    /// ```
927    #[inline(always)]
928    fn complete_err(self) -> impls::CompleteErr<Self, I, O, E>
929    where
930        Self: core::marker::Sized,
931    {
932        impls::CompleteErr {
933            p: self,
934            marker: Default::default(),
935        }
936    }
937
938    /// Convert the parser's error to another type using [`std::convert::From`]
939    #[inline(always)]
940    fn err_into<E2>(self) -> impls::ErrInto<Self, I, O, E, E2>
941    where
942        Self: core::marker::Sized,
943        E: Into<E2>,
944    {
945        impls::ErrInto {
946            parser: self,
947            marker: Default::default(),
948        }
949    }
950
951    /// Recover from an error by skipping everything `recover` consumes and trying again
952    ///
953    /// If `recover` consumes nothing, the error is returned, allowing an alternative recovery
954    /// method.
955    ///
956    /// This commits the parse result, preventing alternative branch paths like with
957    /// [`winnow::combinator::alt`][crate::combinator::alt].
958    #[inline(always)]
959    #[cfg(feature = "unstable-recover")]
960    #[cfg(feature = "std")]
961    fn retry_after<R>(self, recover: R) -> impls::RetryAfter<Self, R, I, O, E>
962    where
963        Self: core::marker::Sized,
964        R: Parser<I, (), E>,
965        I: Stream,
966        I: Recover<E>,
967        E: ParserError<I> + FromRecoverableError<I, E>,
968    {
969        impls::RetryAfter {
970            parser: self,
971            recover,
972            marker: Default::default(),
973        }
974    }
975
976    /// Recover from an error by skipping this parse and everything `recover` consumes
977    ///
978    /// This commits the parse result, preventing alternative branch paths like with
979    /// [`winnow::combinator::alt`][crate::combinator::alt].
980    #[inline(always)]
981    #[cfg(feature = "unstable-recover")]
982    #[cfg(feature = "std")]
983    fn resume_after<R>(self, recover: R) -> impls::ResumeAfter<Self, R, I, O, E>
984    where
985        Self: core::marker::Sized,
986        R: Parser<I, (), E>,
987        I: Stream,
988        I: Recover<E>,
989        E: ParserError<I> + FromRecoverableError<I, E>,
990    {
991        impls::ResumeAfter {
992            parser: self,
993            recover,
994            marker: Default::default(),
995        }
996    }
997}
998
999impl<I, O, E, F> Parser<I, O, E> for F
1000where
1001    F: FnMut(&mut I) -> Result<O, E>,
1002    I: Stream,
1003{
1004    #[inline(always)]
1005    fn parse_next(&mut self, i: &mut I) -> Result<O, E> {
1006        self(i)
1007    }
1008}
1009
1010/// This is a shortcut for [`one_of`][crate::token::one_of].
1011///
1012/// # Example
1013///
1014/// ```rust
1015/// # use winnow::prelude::*;
1016/// # use winnow::{error::ErrMode, error::ContextError};
1017/// fn parser<'s>(i: &mut &'s [u8]) -> ModalResult<u8>  {
1018///     b'a'.parse_next(i)
1019/// }
1020/// assert_eq!(parser.parse_peek(&b"abc"[..]), Ok((&b"bc"[..], b'a')));
1021/// assert!(parser.parse_peek(&b" abc"[..]).is_err());
1022/// assert!(parser.parse_peek(&b"bc"[..]).is_err());
1023/// assert!(parser.parse_peek(&b""[..]).is_err());
1024/// ```
1025impl<I, E> Parser<I, u8, E> for u8
1026where
1027    I: StreamIsPartial,
1028    I: Stream,
1029    I: Compare<u8>,
1030    E: ParserError<I>,
1031{
1032    #[inline(always)]
1033    fn parse_next(&mut self, i: &mut I) -> Result<u8, E> {
1034        crate::token::literal(*self).value(*self).parse_next(i)
1035    }
1036}
1037
1038/// This is a shortcut for [`one_of`][crate::token::one_of].
1039///
1040/// # Example
1041///
1042/// ```rust
1043/// # use winnow::prelude::*;
1044/// # use winnow::{error::ErrMode, error::ContextError};
1045/// fn parser<'s>(i: &mut &'s str) -> ModalResult<char> {
1046///     'a'.parse_next(i)
1047/// }
1048/// assert_eq!(parser.parse_peek("abc"), Ok(("bc", 'a')));
1049/// assert!(parser.parse_peek(" abc").is_err());
1050/// assert!(parser.parse_peek("bc").is_err());
1051/// assert!(parser.parse_peek("").is_err());
1052/// ```
1053impl<I, E> Parser<I, char, E> for char
1054where
1055    I: StreamIsPartial,
1056    I: Stream,
1057    I: Compare<char>,
1058    E: ParserError<I>,
1059{
1060    #[inline(always)]
1061    fn parse_next(&mut self, i: &mut I) -> Result<char, E> {
1062        crate::token::literal(*self).value(*self).parse_next(i)
1063    }
1064}
1065
1066/// This is a shortcut for [`literal`][crate::token::literal].
1067///
1068/// # Example
1069/// ```rust
1070/// # use winnow::prelude::*;
1071/// # use winnow::{error::ErrMode, error::ContextError, error::Needed};
1072/// # use winnow::combinator::alt;
1073/// # use winnow::token::take;
1074///
1075/// fn parser<'s>(s: &mut &'s [u8]) -> ModalResult<&'s [u8]> {
1076///   alt((&"Hello"[..], take(5usize))).parse_next(s)
1077/// }
1078///
1079/// assert_eq!(parser.parse_peek(&b"Hello, World!"[..]), Ok((&b", World!"[..], &b"Hello"[..])));
1080/// assert_eq!(parser.parse_peek(&b"Something"[..]), Ok((&b"hing"[..], &b"Somet"[..])));
1081/// assert!(parser.parse_peek(&b"Some"[..]).is_err());
1082/// assert!(parser.parse_peek(&b""[..]).is_err());
1083/// ```
1084impl<'s, I, E: ParserError<I>> Parser<I, <I as Stream>::Slice, E> for &'s [u8]
1085where
1086    I: Compare<&'s [u8]> + StreamIsPartial,
1087    I: Stream,
1088{
1089    #[inline(always)]
1090    fn parse_next(&mut self, i: &mut I) -> Result<<I as Stream>::Slice, E> {
1091        crate::token::literal(*self).parse_next(i)
1092    }
1093}
1094
1095/// This is a shortcut for [`literal`][crate::token::literal].
1096///
1097/// # Example
1098/// ```rust
1099/// # use winnow::prelude::*;
1100/// # use winnow::{error::ErrMode, error::ContextError, error::Needed};
1101/// # use winnow::combinator::alt;
1102/// # use winnow::token::take;
1103///
1104/// fn parser<'s>(s: &mut &'s [u8]) -> ModalResult<&'s [u8]> {
1105///   alt((b"Hello", take(5usize))).parse_next(s)
1106/// }
1107///
1108/// assert_eq!(parser.parse_peek(&b"Hello, World!"[..]), Ok((&b", World!"[..], &b"Hello"[..])));
1109/// assert_eq!(parser.parse_peek(&b"Something"[..]), Ok((&b"hing"[..], &b"Somet"[..])));
1110/// assert!(parser.parse_peek(&b"Some"[..]).is_err());
1111/// assert!(parser.parse_peek(&b""[..]).is_err());
1112/// ```
1113impl<'s, I, E: ParserError<I>, const N: usize> Parser<I, <I as Stream>::Slice, E> for &'s [u8; N]
1114where
1115    I: Compare<&'s [u8; N]> + StreamIsPartial,
1116    I: Stream,
1117{
1118    #[inline(always)]
1119    fn parse_next(&mut self, i: &mut I) -> Result<<I as Stream>::Slice, E> {
1120        crate::token::literal(*self).parse_next(i)
1121    }
1122}
1123
1124/// This is a shortcut for [`literal`][crate::token::literal].
1125///
1126/// # Example
1127/// ```rust
1128/// # use winnow::prelude::*;
1129/// # use winnow::{error::ErrMode, error::ContextError};
1130/// # use winnow::combinator::alt;
1131/// # use winnow::token::take;
1132///
1133/// fn parser<'s>(s: &mut &'s str) -> ModalResult<&'s str> {
1134///   alt(("Hello", take(5usize))).parse_next(s)
1135/// }
1136///
1137/// assert_eq!(parser.parse_peek("Hello, World!"), Ok((", World!", "Hello")));
1138/// assert_eq!(parser.parse_peek("Something"), Ok(("hing", "Somet")));
1139/// assert!(parser.parse_peek("Some").is_err());
1140/// assert!(parser.parse_peek("").is_err());
1141/// ```
1142impl<'s, I, E: ParserError<I>> Parser<I, <I as Stream>::Slice, E> for &'s str
1143where
1144    I: Compare<&'s str> + StreamIsPartial,
1145    I: Stream,
1146{
1147    #[inline(always)]
1148    fn parse_next(&mut self, i: &mut I) -> Result<<I as Stream>::Slice, E> {
1149        crate::token::literal(*self).parse_next(i)
1150    }
1151}
1152
1153impl<I: Stream, E: ParserError<I>> Parser<I, (), E> for () {
1154    #[inline(always)]
1155    fn parse_next(&mut self, _i: &mut I) -> Result<(), E> {
1156        Ok(())
1157    }
1158}
1159
1160macro_rules! impl_parser_for_tuple {
1161    ($($index:tt $parser:ident $output:ident),+) => (
1162        #[allow(non_snake_case)]
1163        impl<I: Stream, $($output),+, E: ParserError<I>, $($parser),+> Parser<I, ($($output),+,), E> for ($($parser),+,)
1164        where
1165            $($parser: Parser<I, $output, E>),+
1166        {
1167            #[inline(always)]
1168            fn parse_next(&mut self, i: &mut I) -> Result<($($output),+,), E> {
1169                $(let $output = self.$index.parse_next(i)?;)+
1170
1171                Ok(($($output),+,))
1172            }
1173        }
1174    )
1175}
1176
1177macro_rules! impl_parser_for_tuples {
1178    ($index1:tt $parser1:ident $output1:ident, $($index:tt $parser:ident $output:ident),+) => {
1179        impl_parser_for_tuples!(__impl $index1 $parser1 $output1; $($index $parser $output),+);
1180    };
1181    (__impl $($index:tt $parser:ident $output:ident),+; $index1:tt $parser1:ident $output1:ident $(,$index2:tt $parser2:ident $output2:ident)*) => {
1182        impl_parser_for_tuple!($($index $parser $output),+);
1183        impl_parser_for_tuples!(__impl $($index $parser $output),+, $index1 $parser1 $output1; $($index2 $parser2 $output2),*);
1184    };
1185    (__impl $($index:tt $parser:ident $output:ident),+;) => {
1186        impl_parser_for_tuple!($($index $parser $output),+);
1187    }
1188}
1189
1190impl_parser_for_tuples!(
1191  0 P0 O0,
1192  1 P1 O1,
1193  2 P2 O2,
1194  3 P3 O3,
1195  4 P4 O4,
1196  5 P5 O5,
1197  6 P6 O6,
1198  7 P7 O7,
1199  8 P8 O8,
1200  9 P9 O9,
1201  10 P10 O10
1202);
1203
1204#[cfg(feature = "alloc")]
1205use alloc::boxed::Box;
1206
1207#[cfg(feature = "alloc")]
1208impl<I, O, E> Parser<I, O, E> for Box<dyn Parser<I, O, E> + '_> {
1209    #[inline(always)]
1210    fn parse_next(&mut self, i: &mut I) -> Result<O, E> {
1211        (**self).parse_next(i)
1212    }
1213}
1214
1215/// Trait alias for [`Parser`] to be used with [`ModalResult`][crate::error::ModalResult]
1216pub trait ModalParser<I, O, E>: Parser<I, O, crate::error::ErrMode<E>> {}
1217
1218impl<I, O, E, P> ModalParser<I, O, E> for P where P: Parser<I, O, crate::error::ErrMode<E>> {}
1219
1220/// Collect all errors when parsing the input
1221///
1222/// [`Parser`]s will need to use [`Recoverable<I, _>`] for their input.
1223#[cfg(feature = "unstable-recover")]
1224#[cfg(feature = "std")]
1225pub trait RecoverableParser<I, O, R, E> {
1226    /// Collect all errors when parsing the input
1227    ///
1228    /// If `self` fails, this acts like [`Parser::resume_after`] and returns `Ok(None)`.
1229    /// Generally, this should be avoided by using
1230    /// [`Parser::retry_after`] and [`Parser::resume_after`] throughout your parser.
1231    ///
1232    /// The empty `input` is returned to allow turning the errors into [`ParserError`]s.
1233    fn recoverable_parse(&mut self, input: I) -> (I, Option<O>, Vec<R>);
1234}
1235
1236#[cfg(feature = "unstable-recover")]
1237#[cfg(feature = "std")]
1238impl<P, I, O, R, E> RecoverableParser<I, O, R, E> for P
1239where
1240    P: Parser<Recoverable<I, R>, O, E>,
1241    I: Stream,
1242    I: StreamIsPartial,
1243    R: FromRecoverableError<Recoverable<I, R>, E>,
1244    R: core::fmt::Debug,
1245    E: FromRecoverableError<Recoverable<I, R>, E>,
1246    E: ParserError<Recoverable<I, R>>,
1247    E: core::fmt::Debug,
1248{
1249    fn recoverable_parse(&mut self, input: I) -> (I, Option<O>, Vec<R>) {
1250        debug_assert!(
1251            !I::is_partial_supported(),
1252            "partial streams need to handle `ErrMode::Incomplete`"
1253        );
1254
1255        let start = input.checkpoint();
1256        let mut input = Recoverable::new(input);
1257        let start_token = input.checkpoint();
1258        let result = (
1259            self.by_ref(),
1260            crate::combinator::eof.resume_after(crate::token::rest.void()),
1261        )
1262            .parse_next(&mut input);
1263
1264        let (o, err) = match result {
1265            Ok((o, _)) => (Some(o), None),
1266            Err(err) => {
1267                let err_start = input.checkpoint();
1268                let err = R::from_recoverable_error(&start_token, &err_start, &input, err);
1269                (None, Some(err))
1270            }
1271        };
1272
1273        let (mut input, mut errs) = input.into_parts();
1274        input.reset(&start);
1275        if let Some(err) = err {
1276            errs.push(err);
1277        }
1278
1279        (input, o, errs)
1280    }
1281}
1282
1283#[cfg(all(test, feature = "ascii", feature = "binary"))]
1284mod tests {
1285    use super::*;
1286
1287    use snapbox::prelude::*;
1288    use snapbox::str;
1289
1290    use crate::binary::be_u16;
1291    use crate::error::ErrMode;
1292    use crate::error::Needed;
1293    use crate::error::TestResult;
1294    use crate::token::take;
1295    use crate::Partial;
1296
1297    #[doc(hidden)]
1298    #[macro_export]
1299    macro_rules! assert_size (
1300        ($t:ty, $sz:expr) => (
1301            assert!(core::mem::size_of::<$t>() <= $sz, "{} <= {} failed", core::mem::size_of::<$t>(), $sz);
1302        );
1303    );
1304
1305    #[test]
1306    #[cfg(target_pointer_width = "64")]
1307    fn size_test() {
1308        assert_size!(Result<&[u8], (&[u8], u32)>, 40);
1309        assert_size!(Result<&str, u32>, 40);
1310        assert_size!(Needed, 8);
1311        assert_size!(ErrMode<u32>, 16);
1312    }
1313
1314    #[test]
1315    fn err_map_test() {
1316        let e = ErrMode::Backtrack(1);
1317        assert_eq!(e.map(|v| v + 1), ErrMode::Backtrack(2));
1318    }
1319
1320    #[test]
1321    fn single_element_tuples() {
1322        use crate::ascii::alpha1;
1323
1324        let mut parser = (alpha1,);
1325        assert_parse!(
1326            parser.parse_peek("abc123def"),
1327            str![[r#"
1328Ok(
1329    (
1330        "123def",
1331        (
1332            "abc",
1333        ),
1334    ),
1335)
1336
1337"#]]
1338            .raw()
1339        );
1340        assert_parse!(
1341            parser.parse_peek("123def"),
1342            str![[r#"
1343Err(
1344    Backtrack(
1345        InputError {
1346            input: "123def",
1347        },
1348    ),
1349)
1350
1351"#]]
1352            .raw()
1353        );
1354    }
1355
1356    #[test]
1357    fn tuple_test() {
1358        #[allow(clippy::type_complexity)]
1359        fn tuple_3<'i>(
1360            i: &mut Partial<&'i [u8]>,
1361        ) -> TestResult<Partial<&'i [u8]>, (u16, &'i [u8], &'i [u8])> {
1362            (be_u16, take(3u8), "fg").parse_next(i)
1363        }
1364
1365        assert_parse!(
1366            tuple_3.parse_peek(Partial::new(&b"abcdefgh"[..])),
1367            str![[r#"
1368Ok(
1369    (
1370        Partial {
1371            input: [
1372                104,
1373            ],
1374            partial: true,
1375        },
1376        (
1377            24930,
1378            [
1379                99,
1380                100,
1381                101,
1382            ],
1383            [
1384                102,
1385                103,
1386            ],
1387        ),
1388    ),
1389)
1390
1391"#]]
1392            .raw()
1393        );
1394        assert_parse!(
1395            tuple_3.parse_peek(Partial::new(&b"abcd"[..])),
1396            str![[r#"
1397Err(
1398    Incomplete(
1399        Size(
1400            1,
1401        ),
1402    ),
1403)
1404
1405"#]]
1406            .raw()
1407        );
1408        assert_parse!(
1409            tuple_3.parse_peek(Partial::new(&b"abcde"[..])),
1410            str![[r#"
1411Err(
1412    Incomplete(
1413        Unknown,
1414    ),
1415)
1416
1417"#]]
1418            .raw()
1419        );
1420        assert_parse!(
1421            tuple_3.parse_peek(Partial::new(&b"abcdejk"[..])),
1422            str![[r#"
1423Err(
1424    Backtrack(
1425        InputError {
1426            input: Partial {
1427                input: [
1428                    106,
1429                    107,
1430                ],
1431                partial: true,
1432            },
1433        },
1434    ),
1435)
1436
1437"#]]
1438            .raw()
1439        );
1440    }
1441
1442    #[test]
1443    fn unit_type() {
1444        fn parser<'i>(i: &mut &'i str) -> TestResult<&'i str, ()> {
1445            ().parse_next(i)
1446        }
1447        assert_parse!(
1448            parser.parse_peek("abxsbsh"),
1449            str![[r#"
1450Ok(
1451    (
1452        "abxsbsh",
1453        (),
1454    ),
1455)
1456
1457"#]]
1458            .raw()
1459        );
1460        assert_parse!(
1461            parser.parse_peek("sdfjakdsas"),
1462            str![[r#"
1463Ok(
1464    (
1465        "sdfjakdsas",
1466        (),
1467    ),
1468)
1469
1470"#]]
1471            .raw()
1472        );
1473        assert_parse!(
1474            parser.parse_peek(""),
1475            str![[r#"
1476Ok(
1477    (
1478        "",
1479        (),
1480    ),
1481)
1482
1483"#]]
1484            .raw()
1485        );
1486    }
1487}