Created
February 7, 2023 14:19
-
-
Save ChristopherBiscardi/668b89ad5b5be39f0c504e13ee11f4f2 to your computer and use it in GitHub Desktop.
nom custom error examples
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
use color_eyre::eyre::{Result, Context}; | |
use nom::{ | |
bytes::complete::tag, | |
character::complete::alpha1, | |
combinator::rest, | |
error::{ErrorKind, ParseError}, | |
sequence::preceded, | |
*, | |
}; | |
use thiserror::Error; // 1.0.38 | |
#[derive(Error, Debug)] | |
pub enum MyParserError<I> { | |
#[error("nom error")] | |
NomError(#[from] nom::error::Error<I>), | |
#[error("No #+ symbol")] | |
NoHash, | |
} | |
impl<I> ParseError<I> for MyParserError<I> { | |
// on one line, we show the error code and the input that caused it | |
fn from_error_kind(input: I, kind: ErrorKind) -> Self { | |
let nom_error = | |
nom::error::Error::from_error_kind(input, kind); | |
MyParserError::NomError(nom_error) | |
} | |
fn append( | |
input: I, | |
kind: ErrorKind, | |
other: Self, | |
) -> Self { | |
other | |
} | |
} | |
#[derive(Debug, PartialEq)] | |
struct AttributeInfo { | |
name: String, | |
identifier: String, | |
} | |
fn parse( | |
input: &str, | |
) -> IResult<&str, AttributeInfo, MyParserError<&str>> { | |
let result: nom::IResult<&str, &str> = | |
preceded(tag("#+"), alpha1)(input); | |
let Ok((input, name)) = result else { | |
return Err(nom::Err::Failure(MyParserError::NoHash)); | |
}; | |
let (input, identifier) = | |
preceded(tag(": "), rest)(input)?; | |
Ok(( | |
input, | |
AttributeInfo { | |
name: name.to_string(), | |
identifier: identifier.to_string(), | |
}, | |
)) | |
} | |
fn main() -> Result<()> { | |
color_eyre::install()?; | |
let input = "malformatted Short informational text"; | |
let result = parse(input).wrap_err("tried to parse"); | |
dbg!(&result); | |
let output = result.unwrap(); | |
dbg!(output); | |
Ok(()) | |
} | |
#[test] | |
fn parse_works() { | |
let input = "#+TITLE: sdfkljsadflk"; | |
let output = parse(input).unwrap(); | |
assert_eq!( | |
( | |
"", | |
AttributeInfo { | |
name: "TITLE".to_string(), | |
identifier: "sdfkljsadflk".to_string() | |
}, | |
), | |
output | |
); | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
use color_eyre::eyre::{Context, Result}; | |
use nom::{ | |
bytes::complete::tag, character::complete::alpha1, | |
combinator::rest, sequence::preceded, *, | |
}; | |
use nom_supreme::{error::ErrorTree, ParserExt}; | |
#[derive(Debug, PartialEq)] | |
struct AttributeInfo { | |
name: String, | |
identifier: String, | |
} | |
fn parse( | |
input: &str, | |
) -> IResult<&str, AttributeInfo, ErrorTree<&str>> { | |
let (input, name) = preceded( | |
tag("#+") | |
.context("Requires that line starts with `#+`"), | |
alpha1, | |
)(input)?; | |
let (input, identifier) = | |
preceded(tag(": "), rest)(input)?; | |
Ok(( | |
input, | |
AttributeInfo { | |
name: name.to_string(), | |
identifier: identifier.to_string(), | |
}, | |
)) | |
} | |
fn main() -> Result<()> { | |
color_eyre::install()?; | |
let input = "malformatted Short informational text"; | |
let result = parse(input).context("tried to parse"); | |
dbg!(&result); | |
let output = result.unwrap(); | |
dbg!(output); | |
Ok(()) | |
} | |
#[test] | |
fn parse_works() { | |
let input = "#+TITLE: sdfkljsadflk"; | |
let output = parse(input).unwrap(); | |
assert_eq!( | |
( | |
"", | |
AttributeInfo { | |
name: "TITLE".to_string(), | |
identifier: "sdfkljsadflk".to_string() | |
}, | |
), | |
output | |
); | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment