orql 0.1.0

A toy SQL parser for a subset of the Oracle dialect.
Documentation
//! Parses a file and dumps the recognized statements' AST nodes to stdout.

use std::{env, fmt::Debug, fs};

use orql::{
    ast::Statement,
    parser::{self, IterError},
};

// XXX print with comments
fn main() -> Result<(), Box<dyn std::error::Error>> {
    // ~ poor man's cmdline parsing
    let args = env::args().skip(1).collect::<Vec<_>>();
    let (with_locations, files) = match args.first().map(String::as_str) {
        Some("-l") if args.len() > 1 => (true, &args[1..]),
        _ if !args.is_empty() => (false, &args[..]),
        _ => return Err("usage: dump [-l] <files ...>".into()),
    };

    // ~ iterate the files, parse each, and dump their statements' ASTs
    for f in files {
        let s = fs::read_to_string(f)?;
        if with_locations {
            for stmt in parser::iter_with_locations(&s) {
                dump_stmt(stmt)
            }
        } else {
            for stmt in parser::iter(&s) {
                dump_stmt(stmt);
            }
        }
    }
    Ok(())
}

fn dump_stmt<ID: Debug>(stmt: Result<Statement<'_, ID>, IterError>) {
    match stmt {
        Ok(stmt) => {
            println!("-- OK [BEGIN]");
            println!("{stmt:#?}");
            println!("-- OK [END]");
        }
        Err(e) => {
            println!("-- ERR [BEGIN] (Error: {})", e.error);
            println!("{}", &*e.skipped);
            println!("-- ERR [END]");
        }
    }
}