No parser crate

attempt/001
Elijah C. Voigt 1 year ago
parent 6207a7f032
commit 87ca1b13f6

@ -9,7 +9,6 @@ members = [
]
[dependencies]
parser = { path = "crates/parser" }
bevy = { version = "0.14", features = ["file_watcher"] } # , "dynamic_linking"] }
wee_alloc = "*"
bevy_mod_picking = "0.20"

@ -1,12 +0,0 @@
[package]
name = "parser"
version = "0.1.0"
edition = "2021"
[lib]
proc-macro = true
[dependencies]
nom = "7"
syn = "2"
quote = "1"

@ -1,92 +0,0 @@
use proc_macro::TokenStream;
use quote::quote;
use syn::{parse_macro_input, token::Paren, Expr, Ident, Type, TypeTuple};
#[derive(Debug)]
enum Component {
// Members(Vec<Component>),
Member {
tag: Ident,
inputs: Vec<Type>,
}
}
impl syn::parse::Parse for Component {
fn parse(input: syn::parse::ParseStream) -> syn::parse::Result<Self> {
// TODO: Handle components with multiple struct members
let tag: Ident = input.parse()?;
let mut inputs = Vec::new();
while let Ok(ty) = input.parse() {
inputs.push(ty)
}
Ok(Component::Member { tag, inputs })
}
}
///
/// Macro for generating parsing functions for entity components.
///
/// ```
/// let line = "foo 1.2 2.3";
/// let (x, y) = parse!("foo <f32> <f32>")(line).unwrap();
/// ```
///
#[proc_macro]
pub fn parse(tokens: TokenStream) -> TokenStream {
match parse_macro_input!(tokens as Component) {
Component::Member { tag, inputs } => {
// For each input value
// nom::character::complete::space1,
// Match on type to determine parsing function (either float or string likely)
// nom::number::complete::float,
let parsers = Vec::new();
let nom_tuple = quote! {
nom::bytes::complete::tag("#tag"),
#(nom::character::complete::space1, #parsers),*
};
let parsed_vars = Vec::new();
let nom_results = quote! {
#(#parsed_vars),*
};
let nom_output_type = quote! { #(#inputs),* };
let nom_outputs = quote! {
// (x1, x2, ...)
};
let expanded = quote! {
|line: &str| -> Result<#nom_output_type, nom::Err<_>> {
tuple(#nom_tuple)(line).map(|(_, #nom_results)| #nom_outputs)
}
};
TokenStream::from(expanded)
}
}
}
// let t = nom::bytes::complete::take_while1(nom::character::is_alphabetic)(todo!()).unwrap();
// let return_type = todo!();
// let method_body = todo!();
// let return_type = "Result<(f32, f32, f32), nom::Err<()>>";
// let method_body = "
// nom::sequence::tuple((
// nom::bytes::complete::tag(\"thing\"),
// nom::character::complete::space1,
// nom::number::complete::float,
// nom::character::complete::space1,
// nom::number::complete::float,
// nom::character::complete::space1,
// nom::number::complete::float
// ))(line)
// .map(|(_, (_, _, x, _, y, _, z))| {
// (x, y, z)
// })
// ";
// let lambda = format!("|line: &str| -> {} {{ {} }}", return_type, method_body);
// lambda.parse().unwrap()

@ -1,7 +0,0 @@
use parser::parse;
fn main() {
let line = "thing 1.23 3.45 5.67";
let f = parse!(thing f32 f32 f32);
let (_x, _y, _z) = f(line).unwrap();
}

@ -69,17 +69,6 @@ struct GltfScene {
mod parse {
use super::*;
use parser::parse;
#[test]
fn test_parse_macro() {
let line = "thing 1.23 3.45 5.67";
let f = parse!(thing f32 f32 f32);
let result = f(line);
assert_eq!(Ok((1.23, 3.45, 5.67)), result);
}
#[derive(Error, Debug)]
pub(crate) enum SaveEntityParseError {
#[error("Failed to parse Uuid: {0}")]

Loading…
Cancel
Save