tytanic_core/dsl.rs
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126
//! Implementations for the test set DSL. See the language [reference] and
//! [guide] for more info.
//!
//! [reference]: https://tingerrr.github.io/tytanic/reference/test-sets/index.html
//! [guide]: https://tingerrr.github.io/tytanic/guides/test-sets.html
use tytanic_filter::ast::Id;
use tytanic_filter::eval::{self, Context, Error, Func, Set, Value};
use crate::test::Test;
impl eval::Test for Test {
fn id(&self) -> &str {
self.id().as_str()
}
}
/// Creates the default context used by tytanic, this contains bindings for the
/// constructor functions in [`built_in`].
pub fn context() -> Context<Test> {
type FuncPtr =
for<'a, 'b> fn(&'a Context<Test>, &'b [Value<Test>]) -> Result<Value<Test>, Error>;
let mut ctx = Context::new();
let functions = [
("all", built_in::all_ctor as FuncPtr),
("none", built_in::none_ctor),
("skip", built_in::skip_ctor),
("compile_only", built_in::compile_only_ctor),
("ephemeral", built_in::ephemeral_ctor),
("persistent", built_in::persistent_ctor),
];
for (id, func) in functions {
ctx.bind(Id(id.into()), Value::Func(Func::new(func)));
}
ctx
}
/// Function definitions for the tytanic test set DSL default evaluation
/// context.
pub mod built_in {
use tytanic_filter::eval::{Context, Error, Func, Value};
use super::*;
/// The constructor function for the test set returned by [`all`].
pub fn all_ctor(ctx: &Context<Test>, args: &[Value<Test>]) -> Result<Value<Test>, Error> {
Func::expect_no_args("all", ctx, args)?;
Ok(Value::Set(all()))
}
/// Constructor for the `all()` test set. A test set which contains _all_
/// tests.
pub fn all() -> Set<Test> {
Set::new(|_, _| Ok(true))
}
/// The constructor function for the test set returned by [`none`].
pub fn none_ctor(ctx: &Context<Test>, args: &[Value<Test>]) -> Result<Value<Test>, Error> {
Func::expect_no_args("none", ctx, args)?;
Ok(Value::Set(none()))
}
/// Constructor for the `none()` test set. A test set which contains _no_
/// tests.
pub fn none() -> Set<Test> {
Set::new(|_, _| Ok(false))
}
/// The constructor function for the test set returned by [`skip`].
pub fn skip_ctor(ctx: &Context<Test>, args: &[Value<Test>]) -> Result<Value<Test>, Error> {
Func::expect_no_args("skip", ctx, args)?;
Ok(Value::Set(skip()))
}
/// Constructs the `skip()` test set. A test set which contains all tests marked
/// with the `skip` annotation.
pub fn skip() -> Set<Test> {
Set::new(|_, test: &Test| Ok(test.is_skip()))
}
/// The constructor function for the test set returned by [`compile_only`].
pub fn compile_only_ctor(
ctx: &Context<Test>,
args: &[Value<Test>],
) -> Result<Value<Test>, Error> {
Func::expect_no_args("compile-only", ctx, args)?;
Ok(Value::Set(compile_only()))
}
/// Constructs the `compile-only()` test set. A test set which contains all
/// `compile-only` tests.
pub fn compile_only() -> Set<Test> {
Set::new(|_, test: &Test| Ok(test.kind().is_compile_only()))
}
/// The constructor function for the test set returned by [`ephemeral`].
pub fn ephemeral_ctor(ctx: &Context<Test>, args: &[Value<Test>]) -> Result<Value<Test>, Error> {
Func::expect_no_args("ephemeral", ctx, args)?;
Ok(Value::Set(ephemeral()))
}
/// Constructs the `ephemeral()` test set. A test set which contains all
/// `ephemeral` tests.
pub fn ephemeral() -> Set<Test> {
Set::new(|_, test: &Test| Ok(test.kind().is_ephemeral()))
}
/// The constructor function for the test set returned by [`persistent`].
pub fn persistent_ctor(
ctx: &Context<Test>,
args: &[Value<Test>],
) -> Result<Value<Test>, Error> {
Func::expect_no_args("persistent", ctx, args)?;
Ok(Value::Set(persistent()))
}
/// Constructs the `persistent()` test set. A test set which contains all
/// `persistent` tests.
pub fn persistent() -> Set<Test> {
Set::new(|_, test: &Test| Ok(test.kind().is_persistent()))
}
}