forked from gentoo-utils/gentoo-utils
impl DEPEND parser
This commit is contained in:
@@ -348,4 +348,11 @@ mod test {
|
||||
|
||||
assert!(atom().check_finished(it).is_err());
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_atom_with_trailing_dash_and_letter() {
|
||||
let it = InputIter::new("dev-db/mysql-connector-c");
|
||||
|
||||
atom().check_finished(it).unwrap();
|
||||
}
|
||||
}
|
||||
|
||||
18
src/depend/mod.rs
Normal file
18
src/depend/mod.rs
Normal file
@@ -0,0 +1,18 @@
|
||||
use crate::{atom::Atom, useflag::UseFlag};
|
||||
|
||||
pub mod parsers;
|
||||
|
||||
#[derive(Clone, Debug)]
|
||||
pub enum Conditional {
|
||||
Negative(UseFlag),
|
||||
Positive(UseFlag),
|
||||
}
|
||||
|
||||
#[derive(Clone, Debug)]
|
||||
pub enum Expr {
|
||||
Atom(Atom),
|
||||
Conditional(Conditional),
|
||||
AllOf(Vec<Expr>),
|
||||
AnyOf(Vec<Expr>),
|
||||
OneOf(Vec<Expr>),
|
||||
}
|
||||
61
src/depend/parsers.rs
Normal file
61
src/depend/parsers.rs
Normal file
@@ -0,0 +1,61 @@
|
||||
use mon::{DebugTracer, Parser, ParserResult, input::InputIter, mode::Emit, tag, whitespace1};
|
||||
|
||||
use crate::{
|
||||
atom,
|
||||
depend::{Conditional, Expr},
|
||||
useflag,
|
||||
};
|
||||
|
||||
fn expr(it: InputIter<&str>) -> ParserResult<&str, Expr> {
|
||||
let all_of = expr
|
||||
.separated_list1(whitespace1())
|
||||
.delimited_by(tag("(").followed_by(whitespace1()), tag(")"))
|
||||
.map(|exprs| Expr::AllOf(exprs));
|
||||
|
||||
let any_of = expr
|
||||
.separated_list1(whitespace1())
|
||||
.delimited_by(tag("(").followed_by(whitespace1()), tag(")"))
|
||||
.preceded_by(tag("||").followed_by(whitespace1()))
|
||||
.map(|exprs| Expr::AnyOf(exprs));
|
||||
|
||||
let one_of = expr
|
||||
.separated_list1(whitespace1())
|
||||
.delimited_by(tag("(").followed_by(whitespace1()), tag(")"))
|
||||
.preceded_by(tag("^^").followed_by(whitespace1()))
|
||||
.map(|exprs| Expr::OneOf(exprs));
|
||||
|
||||
atom::parsers::atom()
|
||||
.map(|atom| Expr::Atom(atom))
|
||||
.or(conditional().map(|conditional| Expr::Conditional(conditional)))
|
||||
.or(any_of)
|
||||
.or(all_of)
|
||||
.or(one_of)
|
||||
.parse(it)
|
||||
}
|
||||
|
||||
fn conditional<'a>() -> impl Parser<&'a str, Output = Conditional> {
|
||||
useflag::parsers::useflag()
|
||||
.preceded_by(tag("!"))
|
||||
.followed_by(tag("?"))
|
||||
.map(|flag| Conditional::Negative(flag))
|
||||
.or(useflag::parsers::useflag()
|
||||
.followed_by(tag("?"))
|
||||
.map(|flag| Conditional::Positive(flag)))
|
||||
}
|
||||
|
||||
pub fn exprs<'a>() -> impl Parser<&'a str, Output = Vec<Expr>> {
|
||||
expr.separated_list1(whitespace1())
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
mod test {
|
||||
|
||||
use super::*;
|
||||
|
||||
#[test]
|
||||
fn test_expr() {
|
||||
let it = InputIter::new("flag? ( || ( foo/bar foo/bar ) )");
|
||||
|
||||
exprs().check_finished(it).unwrap();
|
||||
}
|
||||
}
|
||||
@@ -2,4 +2,5 @@
|
||||
#![allow(dead_code)]
|
||||
|
||||
pub mod atom;
|
||||
pub mod depend;
|
||||
pub mod useflag;
|
||||
|
||||
27
tests/depend.rs
Normal file
27
tests/depend.rs
Normal file
@@ -0,0 +1,27 @@
|
||||
use gentoo_utils::depend;
|
||||
use mon::{Parser, eof, input::InputIter, tag};
|
||||
use std::fs;
|
||||
|
||||
#[test]
|
||||
fn parse_md5_cache() {
|
||||
let md5_cache = "/var/db/repos/gentoo/metadata/md5-cache";
|
||||
|
||||
for cat in fs::read_dir(md5_cache).unwrap() {
|
||||
for pkg in fs::read_dir(cat.unwrap().path()).unwrap() {
|
||||
let metadata = fs::read_to_string(pkg.unwrap().path()).unwrap();
|
||||
|
||||
for line in metadata.lines() {
|
||||
if line.starts_with("DEPEND=") {
|
||||
eprintln!("{line}");
|
||||
|
||||
depend::parsers::exprs()
|
||||
.ignore()
|
||||
.or(eof())
|
||||
.preceded_by(tag("DEPEND="))
|
||||
.check_finished(InputIter::new(line))
|
||||
.unwrap();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user