spekt
A std::future::Future and Result-based testing trait for managing the lifecycle of stateful, asynchronous tests.
Why spekt:
Most Rust unit tests terminate based on panics (generally triggered by assert!),
with resource clean-up implemented manually through the Drop trait. Working synchronously with a stateful resource
like a database might look like this:
use ;
While this works for many cases, there are a couple of issues with this recommendation:
- Technically, Rust doesn't guarantee that
Dropwill be run, and one shouldn't rely onDropto be run in all cases. Dropalso cannot be asynchronous! There has been much discussion around Asynchronous destructors, but no reliable destructor trait has yet materialized forasyncfunctions.panic-based assertions (and their associated unwinding) also behave in ways that might be unpredictable across runtimes. This is, specifically, an issue in tests for which there is no good universal solution.- In addition, while
newandDropmake sense for resources, those conventions make less sense for the more abstract idea of a "Test". In most testing frameworks, the idea of a "test" is the combination of a some stateful test context initializedbeforethe actual test, a test case that can mutate its own context, and some clean-up to be runafterthe actual test.
spekt avoids all of these issues by providing a Test trait
that encompasses the before -> test -> after lifecycle of stateful async tests that use Result to drive assertions.
How to use:
spekt::Test can be implemented for any Send + Sync test state, enabling a test() method that returns a std::future::Future.
The returned Future is runtime-agnostic, and can be evaluated synchronously with .wait(), through a per-suite custom runtime
(e.g. tokio::runtime::Runtime),
or through an async test-runner like tokio::test.
Rewriting the example above with spekt::Test:
use ;
use Test;
// spekt optionally re-exports async_trait
// any executor will do, but tokio::test is recommended
async
Roadmap
- Include a
Suiteabstraction for multipleTestthat share a context - Handle custom assertion libraries like
rust-pretty-assertions - Handle custom test frameworks