Several changes, see commit msg
* clean up all tests * bugfix for zero value functions, and test * removed expand function, put in snippets * added doc strings to Symbol type * added doc strings to symbol declarations * implemented display for Args type * wrote a help function * wrote docstrings for all builtins and config vars
This commit is contained in:
parent
4b587f11ab
commit
dc6342bc74
16 changed files with 575 additions and 677 deletions
|
|
@ -10,6 +10,7 @@ mod func_tests {
|
|||
let test_internal_func: Symbol = Symbol {
|
||||
name: String::from("test_func_in"),
|
||||
conditional_branches: false,
|
||||
docs: String::new(),
|
||||
args: Args::Strict(vec![Type::Bool]),
|
||||
value: ValueType::Internal(Rc::new(
|
||||
|a: &Seg, _: &mut SymTable| -> Result<Ctr, String> {
|
||||
|
|
@ -23,95 +24,63 @@ mod func_tests {
|
|||
)),
|
||||
};
|
||||
let args = Seg::from(Box::new(Ctr::Bool(true)), Box::new(Ctr::None));
|
||||
|
||||
syms.insert(String::from("test_func_in"), test_internal_func);
|
||||
|
||||
if let Ok(ret) = syms.call_symbol(&"test_func_in".to_string(), &args, true) {
|
||||
match *ret {
|
||||
Ctr::Bool(b) => assert!(b),
|
||||
_ => {
|
||||
print!("invalid return from func!");
|
||||
assert!(false);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
print!("call to function failed!");
|
||||
assert!(false);
|
||||
if let Ctr::Bool(b) = *syms.call_symbol(&"test_func_in".to_string(), &args, true).unwrap() {
|
||||
assert!(b)
|
||||
}
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn decl_and_call_external_func_singlet() {
|
||||
let mut syms = SymTable::new();
|
||||
match lex(&"input".to_string()) {
|
||||
Err(e) => panic!("{}", e),
|
||||
Ok(finner) => {
|
||||
let test_external_func: Symbol = Symbol {
|
||||
name: String::from("echo"),
|
||||
conditional_branches: false,
|
||||
args: Args::Lazy(1),
|
||||
value: ValueType::FuncForm(UserFn {
|
||||
arg_syms: vec!["input".to_string()],
|
||||
ast: finner,
|
||||
}),
|
||||
};
|
||||
let finner = lex(&"input".to_string()).unwrap();
|
||||
let test_external_func: Symbol = Symbol {
|
||||
name: String::from("echo"),
|
||||
conditional_branches: false,
|
||||
args: Args::Lazy(1),
|
||||
docs: String::new(),
|
||||
value: ValueType::FuncForm(UserFn {
|
||||
arg_syms: vec!["input".to_string()],
|
||||
ast: finner,
|
||||
}),
|
||||
};
|
||||
|
||||
let args = Seg::from(
|
||||
Box::new(Ctr::String("test".to_string())),
|
||||
Box::new(Ctr::None),
|
||||
);
|
||||
let args = Seg::from(
|
||||
Box::new(Ctr::String("test".to_string())),
|
||||
Box::new(Ctr::None),
|
||||
);
|
||||
|
||||
syms.insert(String::from("test_func_in"), test_external_func);
|
||||
|
||||
match syms.call_symbol(&"test_func_in".to_string(), &args, true) {
|
||||
Ok(ret) => match *ret {
|
||||
Ctr::String(b) => assert!(b == "test"),
|
||||
_ => {
|
||||
print!("Invalid return from func. Got {:?}\n", ret);
|
||||
assert!(false);
|
||||
}
|
||||
},
|
||||
Err(e) => {
|
||||
print!("Call to function failed: {}\n", e);
|
||||
assert!(false);
|
||||
}
|
||||
}
|
||||
}
|
||||
syms.insert(String::from("test_func_in"), test_external_func);
|
||||
if let Ctr::Bool(b) = *syms.call_symbol(&"test_func_in".to_string(), &args, true).unwrap() {
|
||||
assert!(b)
|
||||
}
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn decl_and_call_external_func_multi_body() {
|
||||
let mut syms = SymTable::new();
|
||||
match lex(&"(input input)".to_string()) {
|
||||
Err(e) => panic!("{}", e),
|
||||
Ok(finner) => {
|
||||
let test_external_func: Symbol = Symbol {
|
||||
name: String::from("echo_2"),
|
||||
conditional_branches: false,
|
||||
args: Args::Lazy(1),
|
||||
value: ValueType::FuncForm(UserFn {
|
||||
arg_syms: vec!["input".to_string()],
|
||||
ast: finner,
|
||||
}),
|
||||
};
|
||||
let finner = lex(&"input".to_string()).unwrap();
|
||||
let test_external_func: Symbol = Symbol {
|
||||
name: String::from("echo_2"),
|
||||
conditional_branches: false,
|
||||
args: Args::Lazy(1),
|
||||
docs: String::new(),
|
||||
value: ValueType::FuncForm(UserFn {
|
||||
arg_syms: vec!["input".to_string()],
|
||||
ast: finner,
|
||||
}),
|
||||
};
|
||||
|
||||
let args = Seg::from(
|
||||
Box::new(Ctr::String("test".to_string())),
|
||||
Box::new(Ctr::None),
|
||||
);
|
||||
let args = Seg::from(
|
||||
Box::new(Ctr::String("test".to_string())),
|
||||
Box::new(Ctr::None),
|
||||
);
|
||||
|
||||
syms.insert(String::from("echo_2"), test_external_func);
|
||||
|
||||
match syms.call_symbol(&"echo_2".to_string(), &args, true) {
|
||||
Ok(ret) => assert_eq!(ret.to_string(), "'test'"),
|
||||
Err(e) => {
|
||||
print!("Call to function failed: {}\n", e);
|
||||
assert!(false);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
syms.insert(String::from("echo_2"), test_external_func);
|
||||
assert_eq!(*syms.call_symbol(&"echo_2".to_string(), &args, true)
|
||||
.unwrap()
|
||||
.to_string(),
|
||||
"'test'".to_string());
|
||||
}
|
||||
|
||||
#[test]
|
||||
|
|
@ -121,6 +90,7 @@ mod func_tests {
|
|||
name: String::from("test_inner"),
|
||||
conditional_branches: false,
|
||||
args: Args::Strict(vec![Type::Bool]),
|
||||
docs: String::new(),
|
||||
value: ValueType::Internal(Rc::new(
|
||||
|a: &Seg, _: &mut SymTable| -> Result<Ctr, String> {
|
||||
let inner = a;
|
||||
|
|
@ -137,39 +107,25 @@ mod func_tests {
|
|||
)),
|
||||
};
|
||||
|
||||
match lex(&"((test_inner true))".to_string()) {
|
||||
Err(e) => panic!("{}", e),
|
||||
Ok(finner) => {
|
||||
let outer_func: Symbol = Symbol {
|
||||
name: String::from("test_outer"),
|
||||
conditional_branches: false,
|
||||
args: Args::Lazy(1),
|
||||
value: ValueType::FuncForm(UserFn {
|
||||
arg_syms: vec!["input".to_string()],
|
||||
ast: finner,
|
||||
}),
|
||||
};
|
||||
let finner = lex(&"((test_inner true))".to_string()).unwrap();
|
||||
let outer_func: Symbol = Symbol {
|
||||
name: String::from("test_outer"),
|
||||
conditional_branches: false,
|
||||
args: Args::Lazy(1),
|
||||
docs: String::new(),
|
||||
value: ValueType::FuncForm(UserFn {
|
||||
arg_syms: vec!["input".to_string()],
|
||||
ast: finner,
|
||||
}),
|
||||
};
|
||||
|
||||
let args = Seg::from(Box::new(Ctr::Bool(true)), Box::new(Ctr::None));
|
||||
|
||||
syms.insert(String::from("test_inner"), inner_func);
|
||||
syms.insert(String::from("test_outer"), outer_func);
|
||||
|
||||
match syms.call_symbol(&"test_outer".to_string(), &args, true) {
|
||||
Ok(ret) => match *ret {
|
||||
Ctr::String(b) => assert!(b == "test"),
|
||||
_ => {
|
||||
print!("Invalid return from func. Got {:?}\n", ret);
|
||||
assert!(false);
|
||||
}
|
||||
},
|
||||
Err(e) => {
|
||||
print!("Call to function failed: {}\n", e);
|
||||
assert!(false);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
let args = Seg::from(Box::new(Ctr::Bool(true)), Box::new(Ctr::None));
|
||||
syms.insert(String::from("test_inner"), inner_func);
|
||||
syms.insert(String::from("test_outer"), outer_func);
|
||||
assert_eq!(syms.call_symbol(&"test_outer".to_string(), &args, true)
|
||||
.unwrap()
|
||||
.to_string(),
|
||||
"'test'".to_string());
|
||||
}
|
||||
|
||||
#[test]
|
||||
|
|
@ -179,6 +135,7 @@ mod func_tests {
|
|||
name: String::from("test_func_in"),
|
||||
conditional_branches: false,
|
||||
args: Args::Strict(vec![Type::Bool]),
|
||||
docs: String::new(),
|
||||
value: ValueType::Internal(Rc::new(
|
||||
|a: &Seg, _: &mut SymTable| -> Result<Ctr, String> {
|
||||
let inner = a;
|
||||
|
|
@ -193,75 +150,66 @@ mod func_tests {
|
|||
let args = Seg::from(Box::new(Ctr::Integer(1)), Box::new(Ctr::None));
|
||||
|
||||
syms.insert(String::from("test_func_in"), test_internal_func);
|
||||
|
||||
if let Err(s) = syms.call_symbol(&"test_func_in".to_string(), &args, true) {
|
||||
assert_eq!(s, "failure to call test_func_in: arg 1 expected to be bool");
|
||||
} else {
|
||||
print!("call to function succeeded (shouldnt have)");
|
||||
assert!(false);
|
||||
}
|
||||
assert_eq!(
|
||||
syms.call_symbol(&"test_func_in".to_string(), &args, true)
|
||||
.err()
|
||||
.unwrap(),
|
||||
"arg 1 expected to be bool".to_string(),
|
||||
);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn too_many_args() {
|
||||
let mut syms = SymTable::new();
|
||||
match lex(&"(input)".to_string()) {
|
||||
Err(e) => panic!("{}", e),
|
||||
Ok(finner) => {
|
||||
let test_external_func: Symbol = Symbol {
|
||||
name: String::from("echo"),
|
||||
conditional_branches: false,
|
||||
args: Args::Lazy(1),
|
||||
value: ValueType::FuncForm(UserFn {
|
||||
arg_syms: vec!["input".to_string()],
|
||||
ast: finner,
|
||||
}),
|
||||
};
|
||||
let finner = lex(&"(input)".to_string()).unwrap();
|
||||
let test_external_func: Symbol = Symbol {
|
||||
name: String::from("echo"),
|
||||
conditional_branches: false,
|
||||
args: Args::Lazy(1),
|
||||
docs: String::new(),
|
||||
value: ValueType::FuncForm(UserFn {
|
||||
arg_syms: vec!["input".to_string()],
|
||||
ast: finner,
|
||||
}),
|
||||
};
|
||||
|
||||
let args = Seg::from(
|
||||
Box::new(Ctr::String("test".to_string())),
|
||||
Box::new(Ctr::Seg(Seg::from_mono(Box::new(Ctr::Integer(1))))),
|
||||
);
|
||||
let args = Seg::from(
|
||||
Box::new(Ctr::String("test".to_string())),
|
||||
Box::new(Ctr::Seg(Seg::from_mono(Box::new(Ctr::Integer(1))))),
|
||||
);
|
||||
|
||||
syms.insert(String::from("test_func_in"), test_external_func);
|
||||
|
||||
if let Err(s) = syms.call_symbol(&"test_func_in".to_string(), &args, true) {
|
||||
assert_eq!(s, "failure to call echo: expected 1 args. Got 2.");
|
||||
} else {
|
||||
print!("call to function succeeded (shouldnt have)");
|
||||
assert!(false);
|
||||
}
|
||||
}
|
||||
}
|
||||
syms.insert(String::from("test_func_in"), test_external_func);
|
||||
assert_eq!(
|
||||
syms.call_symbol(&"test_func_in".to_string(), &args, true)
|
||||
.err()
|
||||
.unwrap(),
|
||||
"expected 1 args. Got 2.".to_string(),
|
||||
);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn too_few_args() {
|
||||
let mut syms = SymTable::new();
|
||||
match lex(&"(input)".to_string()) {
|
||||
Err(e) => panic!("{}", e),
|
||||
Ok(finner) => {
|
||||
let test_external_func: Symbol = Symbol {
|
||||
name: String::from("echo"),
|
||||
conditional_branches: false,
|
||||
args: Args::Lazy(1),
|
||||
value: ValueType::FuncForm(UserFn {
|
||||
arg_syms: vec!["input".to_string()],
|
||||
ast: finner,
|
||||
}),
|
||||
};
|
||||
let finner = lex(&"(input)".to_string()).unwrap();
|
||||
let test_external_func: Symbol = Symbol {
|
||||
name: String::from("echo"),
|
||||
conditional_branches: false,
|
||||
args: Args::Lazy(1),
|
||||
docs: String::new(),
|
||||
value: ValueType::FuncForm(UserFn {
|
||||
arg_syms: vec!["input".to_string()],
|
||||
ast: finner,
|
||||
}),
|
||||
};
|
||||
|
||||
let args = Seg::new();
|
||||
syms.insert(String::from("test_func_in"), test_external_func);
|
||||
|
||||
if let Err(s) = syms.call_symbol(&"test_func_in".to_string(), &args, true) {
|
||||
assert_eq!(s, "failure to call echo: expected 1 args. Got 0.");
|
||||
} else {
|
||||
print!("call to function succeeded (shouldnt have)");
|
||||
assert!(false);
|
||||
}
|
||||
}
|
||||
}
|
||||
let args = Seg::new();
|
||||
syms.insert(String::from("test_func_in"), test_external_func);
|
||||
assert_eq!(
|
||||
syms.call_symbol(&"test_func_in".to_string(), &args, true)
|
||||
.err()
|
||||
.unwrap(),
|
||||
"expected 1 args. Got 0.".to_string(),
|
||||
);
|
||||
}
|
||||
|
||||
#[test]
|
||||
|
|
@ -271,6 +219,7 @@ mod func_tests {
|
|||
name: String::from("test_func_in"),
|
||||
conditional_branches: false,
|
||||
args: Args::Strict(vec![Type::Bool]),
|
||||
docs: String::new(),
|
||||
value: ValueType::Internal(Rc::new(
|
||||
|a: &Seg, _: &mut SymTable| -> Result<Ctr, String> {
|
||||
let inner = a;
|
||||
|
|
@ -288,15 +237,12 @@ mod func_tests {
|
|||
);
|
||||
|
||||
syms.insert(String::from("test_func_in"), test_internal_func);
|
||||
|
||||
if let Err(s) = syms.call_symbol(&"test_func_in".to_string(), &args, true) {
|
||||
assert_eq!(
|
||||
s,
|
||||
"error in call to undefined-symbol: undefined symbol: undefined-symbol"
|
||||
);
|
||||
} else {
|
||||
print!("call to function succeeded (shouldnt have)");
|
||||
assert!(false);
|
||||
}
|
||||
assert_eq!(
|
||||
syms.call_symbol(&"test_func_in".to_string(), &args, true)
|
||||
.err()
|
||||
.unwrap(),
|
||||
"error in call to undefined-symbol: undefined symbol: undefined-symbol"
|
||||
.to_string(),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue