Function kparse::combinators::track

source ·
pub fn track<PA, C, I, O, E>(
    func: C,
    parser: PA
) -> impl FnMut(I) -> Result<(I, O), Err<E>>where
    PA: Parser<I, O, E>,
    C: Code,
    I: Clone + Debug + TrackedSpan<C> + InputTake + InputLength + InputIter + AsBytes,
    Err<E>: KParseError<C, I>,
Expand description

Tracked execution of a parser.

use nom::bytes::complete::tag;
use nom::Parser;
use kparse::combinators::{err_into, with_code, track, map_res};
use kparse::examples::{ExParserResult, ExSpan, ExTagB, ExTokenizerResult};
use kparse::KParseError;

fn parse_b(input: ExSpan<'_>) -> ExParserResult<'_, AstB> {
    err_into(track(ExTagB,
        map_res(nom_parse_b, |span| Ok(AstB { span }))
    ))(input)
}

fn nom_parse_b(i: ExSpan<'_>) -> ExTokenizerResult<'_, ExSpan<'_>> {
    with_code(tag("b"), ExTagB).parse(i)
}

struct AstB<'s> {
    pub span: ExSpan<'s>,
}

The same can be achieved in a imperative style.

use nom::bytes::complete::tag;
use nom::Parser;
use kparse::{Track, KParser};
use kparse::examples::{ExParserResult, ExSpan, ExTagA, ExTokenizerResult};
use kparse::prelude::*;

fn parse_a(input: ExSpan<'_>) -> ExParserResult<'_, AstA> {
    Track.enter(ExTagA, input);
    let (rest, tok) = nom_parse_a.err_into().parse(input).track()?;
    Track.ok(rest, tok, AstA { span: tok })
}

fn nom_parse_a(i: ExSpan<'_>) -> ExTokenizerResult<'_, ExSpan<'_>> {
    tag("a").with_code(ExTagA).parse(i)
}

#[derive(Debug)]
struct AstA<'s> {
    pub span: ExSpan<'s>,
}