rigz_core/
lib.rs

1use serde::{Deserialize, Serialize};
2use std::collections::HashMap;
3use std::fmt::Result;
4use std::fmt::{Display, Formatter};
5use std::fs::File;
6use std::path::PathBuf;
7
8#[derive(Clone, Debug, PartialEq, Deserialize, Serialize)]
9pub enum Argument {
10    None,
11    Int(i32),
12    Long(i64),
13    Float(f32),
14    Double(f64),
15    Bool(bool),
16    String(String),
17    File(RigzFile),
18    Object(HashMap<String, Argument>),
19    List(Vec<Argument>),
20    FunctionCall(FunctionCall),
21    Definition(Definition),
22    Error(String),
23}
24
25#[derive(Debug, Deserialize, Serialize)]
26pub struct RigzFile {
27    pub file: PathBuf,
28    #[serde(skip_serializing, skip_deserializing)]
29    internal: Option<File>,
30}
31
32impl RigzFile {
33    pub fn file(self) -> Option<File> {
34        self.internal
35    }
36}
37
38impl Display for RigzFile {
39    fn fmt(&self, f: &mut Formatter<'_>) -> Result {
40        write!(f, "{}", self.file.to_str().unwrap_or("<invalid-utf>"))
41    }
42}
43
44impl Clone for RigzFile {
45    fn clone(&self) -> Self {
46        let file = self.file.clone();
47        if file.exists() {
48            RigzFile {
49                internal: Some(File::open(&file).expect("Failed to open file")),
50                file,
51            }
52        } else {
53            RigzFile {
54                file,
55                internal: None,
56            }
57        }
58    }
59}
60
61impl PartialEq for RigzFile {
62    fn eq(&self, other: &Self) -> bool {
63        self.file == other.file
64    }
65}
66
67#[derive(Clone, Debug, PartialEq, Deserialize, Serialize)]
68#[repr(C)]
69pub enum Definition {
70    None,
71    One(HashMap<String, Argument>),
72    Many(Vec<Argument>),
73}
74
75impl Display for Argument {
76    fn fmt(&self, f: &mut Formatter<'_>) -> Result {
77        match self {
78            Argument::None => write!(f, "none"),
79            Argument::Int(i) => write!(f, "{}", i),
80            Argument::Long(l) => write!(f, "{}", l),
81            Argument::Float(fl) => write!(f, "{}", fl),
82            Argument::Double(d) => write!(f, "{}", d),
83            Argument::Bool(b) => write!(f, "{}", b),
84            Argument::String(s) => write!(f, "{}", s),
85            Argument::Object(o) => write!(f, "{:?}", o),
86            Argument::List(l) => write!(f, "{:?}", l),
87            Argument::FunctionCall(fc) => write!(f, "{:?}", fc),
88            Argument::Definition(d) => write!(f, "{:?}", d),
89            Argument::Error(e) => write!(f, "Error: {}", e),
90            Argument::File(file) => write!(f, "{}", file),
91        }
92    }
93}
94
95#[derive(Clone, Debug, PartialEq, Deserialize, Serialize)]
96pub struct FunctionCall {
97    pub name: String,
98    pub args: Vec<Argument>,
99    pub definition: Definition,
100}
101
102#[derive(Debug, PartialEq)]
103pub enum RuntimeStatus<T> {
104    Ok(T),
105    NotFound,
106    Err(String),
107}
108
109pub trait Module {
110    fn name(&self) -> &str;
111
112    fn root(&self) -> PathBuf;
113
114    fn function_call(
115        &self,
116        name: &str,
117        arguments: Vec<Argument>,
118        definition: Definition,
119        prior_result: Argument,
120    ) -> RuntimeStatus<Argument>;
121
122    fn initialize(&self, args: InitializationArgs) -> RuntimeStatus<()> {
123        if args.all_errors_fatal {
124            RuntimeStatus::Err("Initialization Function Not Found".into())
125        } else {
126            RuntimeStatus::NotFound
127        }
128    }
129}
130
131
132#[derive(Clone, Copy)]
133pub struct InitializationArgs {
134    pub all_errors_fatal: bool,
135    pub ignore_symbol_not_found: bool,
136    pub prefer_none_over_prior_result: bool,
137    pub require_aliases: bool,
138}