An RSpec inspired minimal testing framework for Rust.
This is a fork of the original speculate.rs by @utkarshkukreti, now maintained by the Altertable.ai team.
Since this crate is not yet published to crates.io, add speculate to the dev-dependencies section of your Cargo.toml using the GitHub repository:
[dev-dependencies]
speculate = { git = "https://github.com/altertable-ai/speculate.rs" }And add the following to the top of the Rust file you want to add tests for:
#[cfg(test)]
extern crate speculate;
#[cfg(test)]
use speculate::speculate; // Must be imported into the current scope.Speculate provides the speculate! syntax extension.
Inside speculate! { ... }, you can have any "Item", like static, const,
fn, etc, and 5 special types of blocks:
-
describe(or its aliascontext) - to group tests in a hierarchy, for readability. Can be arbitrarily nested. -
before- contains setup code that's inserted before every sibling and nesteditblocks. -
after- contains teardown code that's inserted after every sibling and nesteditblocks. -
it(or its aliastest) - contains tests.For example:
it can_add_1_and_2 { assert_eq!(1 + 2, 3); }
You can optionally add attributes to this block:
#[ignore] test ignore { assert_eq!(1, 2); } #[should_panic] test should_panic { assert_eq!(1, 2); } #[should_panic(expected = "foo")] test should_panic_with_foo { panic!("foo"); }
extern crate speculate;
use speculate::speculate;
speculate! {
const ZERO: i32 = 0;
fn add(a: i32, b: i32) -> i32 {
a + b
}
describe "math" {
const ONE: i32 = 1;
fn sub(a: i32, b: i32) -> i32 {
a - b
}
before {
let two = ONE + ONE;
}
it can_add_stuff {
assert_eq!(ONE, add(ZERO, ONE));
assert_eq!(two, add(ONE, ONE));
}
it can_subtract_stuff {
assert_eq!(ZERO, sub(ONE, ONE));
assert_eq!(ONE, sub(two, ONE));
}
context "nested context with additional details" {
before {
let three = two + ONE;
}
it can_add_stuff_in_nested_context {
assert_eq!(three, add(two, ONE));
}
}
}
}Important: Rust's rustfmt cannot automatically format code inside procedural macro invocations like speculate!. This is a known limitation - rustfmt only formats inside declarative macros (macro_rules!), not procedural macros.
Therefore, you must manually ensure proper indentation inside speculate! blocks:
- Use 4 spaces for indentation (no tabs)
- Maintain consistent indentation levels
- Follow the examples in the README and test files
Contributions are welcome! Please feel free to submit a Pull Request.
When contributing, please ensure:
-
Indentation inside
speculate!blocks: Use exactly 4 spaces (no tabs)- This cannot be automatically checked by rustfmt
- Review your code carefully before submitting
- Follow the indentation pattern in existing test files
-
Run
cargo +nightly fmtbefore committing to format code outside macros -
All tests pass: Run
cargo testto verify -
No clippy warnings: Run
cargo clippyto check for issues
The CI will check formatting and run tests, but manual indentation inside macros must be verified by the contributor.
MIT License - see the LICENSE file for details.