pub mod ast;
pub mod error;
pub mod executor;
pub mod lexer;
pub mod modules;
pub mod parser;
pub mod stream;
pub mod value;
pub use error::RobinPathError;
pub use executor::{BuiltinCallback, BuiltinFn, Environment};
pub use value::Value;
use executor::Executor;
use lexer::Lexer;
use parser::Parser;
pub struct RobinPath {
executor: Executor,
}
impl RobinPath {
pub fn new() -> Self {
let mut env = Environment::new();
modules::register_all_modules(&mut env);
Self {
executor: Executor::new(env),
}
}
pub fn with_environment(env: Environment) -> Self {
Self {
executor: Executor::new(env),
}
}
pub fn parse(source: &str) -> Result<Vec<ast::Stmt>, RobinPathError> {
let tokens = Lexer::new(source).tokenize()?;
let stmts = Parser::new(tokens).parse()?;
Ok(stmts)
}
pub fn execute(&mut self, source: &str) -> Result<Value, RobinPathError> {
let stmts = Self::parse(source)?;
self.executor.execute(&stmts)
}
pub fn execute_ast(&mut self, stmts: &[ast::Stmt]) -> Result<Value, RobinPathError> {
self.executor.execute(stmts)
}
pub fn output(&self) -> &[String] {
&self.executor.environment.output
}
pub fn clear_output(&mut self) {
self.executor.environment.output.clear();
}
pub fn get_variable(&self, name: &str) -> Option<&Value> {
self.executor.environment.variables.get(name)
}
pub fn set_variable(&mut self, name: &str, value: Value) {
self.executor.environment.variables.insert(name.to_string(), value);
}
pub fn register_builtin(
&mut self,
name: &str,
func: impl Fn(&[Value], Option<&BuiltinCallback>) -> Result<Value, String> + Send + Sync + 'static,
) {
self.executor.environment.register_builtin(name, func);
}
}
impl Default for RobinPath {
fn default() -> Self {
Self::new()
}
}