首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >使用nom与nom_locate一起使用短错误消息

使用nom与nom_locate一起使用短错误消息
EN

Stack Overflow用户
提问于 2022-02-28 00:26:01
回答 1查看 275关注 0票数 0

我试图在nom_locate中使用nom进行解析,并遵循本教程。我只想要格式的输出:

代码语言:javascript
复制
Error: line 5, column 1

但目前我得到:

代码语言:javascript
复制
Error: Parsing Failure: ParseError { span: LocatedSpan { offset: 37, line: 5, fragment: "{{G]\nK(1)key [J]\n", extra: () }, message: "Error: line 5, column 1" }

相关守则:

代码语言:javascript
复制
pub type Span<'a> = LocatedSpan<&'a str>;
pub type IResult<'a, O> = nom::IResult<Span<'a>, O, ParseError<'a>>;


#[derive(Debug, PartialEq)]
pub struct ParseError<'a> {
    span: Span<'a>,
    message: String,
}

impl<'a> ParseError<'a> {
    pub fn new(message: String, span: Span<'a>) -> Self {
        Self {
            span,
            message,
        }
    }
}

impl<'a> nom::error::ParseError<Span<'a>> for ParseError<'a> {
    fn from_error_kind(input: Span<'a>, _: nom::error::ErrorKind) -> Self {
        Self::new(format!("Error: line {}, column {}", input.location_line(), input.location_line()), input)
    }

    fn append(input: Span<'a>, _: nom::error::ErrorKind, _: Self) -> Self {
        Self::new(format!("Error: line {}, column {}", input.location_line(), input.location_line()), input)
    }

    fn from_char(input: Span<'a>, _: char) -> Self {
        Self::new(format!("Error: line {}, column {}", input.location_line(), input.location_line()), input)
    }
}

pub fn job(s: Span) -> IResult<Vec<entities::Step>> {
    let (s, steps) = many1(job_lines)(s)?;
    Ok((s, steps))
}

fn job_lines(s: Span) -> IResult<entities::Step> {
    let (s, name) = match step_name(s) {
        Ok((s, name)) => (s, name),
        Err(nom::Err::Error(_)) => {
            let line = s.location_line();
            let column = s.get_column();
            return Err(nom::Err::Failure(ParseError::new(
                format!("Error: line {}, column {}", line, column),
                s,
            )));
        },
        Err(e) => return Err(e),
    };

    Ok((s, name))
}

相关错误代码(主要是:

代码语言:javascript
复制
    let steps = match input::parsers::job(input::parsers::Span::new(&input)) {
        Ok((_, steps)) => steps,
        Err(error) => {
            eprintln!("{}", error);
            std::process::exit(1)
        }
    };

我需要做什么才能得到短错误消息而不是泛泛的错误消息?

编辑:我从自定义ParseError中删除了span属性,然后错误输出变成:

代码语言:javascript
复制
Parsing Failure: ParseError { message: "Error: line 5, column 1" }

好得多,但问题依然存在:除了信息本身,我还能得到所有的东西吗?

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2022-02-28 08:23:43

正如您所推测的,error是一个nom::Err::Err,它是一个enum,因此您需要匹配它才能得到内部错误:

代码语言:javascript
复制
    let steps = match input::parsers::job(input::parsers::Span::new(&input)) {
        Ok((_, steps)) => steps,
        Err(nom::Err::Failure (error)) => {
            eprintln!("{}", error.message);
            std::process::exit(1)
        },
        Err(error) => {
            eprintln!("Unknown error: {}", error);
            std::process::exit(1)
        },
    };
票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/71289514

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档