pub struct Cucumber<W, P, I, R, Wr, Cli = Empty> where
W: World,
P: Parser<I>,
R: Runner<W>,
Wr: Writer<W>,
Cli: Args, { /* private fields */ }
Expand description
Top-level Cucumber executor.
Most of the time you don’t need to work with it directly, just use
WorldInit::run()
or WorldInit::cucumber()
on your World
deriver
to get Cucumber up and running.
Otherwise use Cucumber::new()
to get the default Cucumber executor,
provide Step
s with WorldInit::collection()
or by hand with
Cucumber::given()
, Cucumber::when()
and Cucumber::then()
.
In case you want a custom Parser
, Runner
or Writer
, or some
other finer control, use Cucumber::custom()
or
Cucumber::with_parser()
, Cucumber::with_runner()
and
Cucumber::with_writer()
to construct your dream Cucumber executor!
Implementations
pub fn with_parser<NewP, NewI>(
self,
parser: NewP
) -> Cucumber<W, NewP, NewI, R, Wr, Cli> where
NewP: Parser<NewI>,
pub fn with_parser<NewP, NewI>(
self,
parser: NewP
) -> Cucumber<W, NewP, NewI, R, Wr, Cli> where
NewP: Parser<NewI>,
Replaces Parser
.
pub fn with_runner<NewR>(self, runner: NewR) -> Cucumber<W, P, I, NewR, Wr, Cli> where
NewR: Runner<W>,
pub fn with_runner<NewR>(self, runner: NewR) -> Cucumber<W, P, I, NewR, Wr, Cli> where
NewR: Runner<W>,
Replaces Runner
.
pub fn with_writer<NewWr>(
self,
writer: NewWr
) -> Cucumber<W, P, I, R, NewWr, Cli> where
NewWr: Writer<W>,
pub fn with_writer<NewWr>(
self,
writer: NewWr
) -> Cucumber<W, P, I, R, NewWr, Cli> where
NewWr: Writer<W>,
Replaces Writer
.
pub fn repeat_skipped(self) -> Cucumber<W, P, I, R, Repeat<W, Wr>, Cli> where
Wr: NonTransforming,
pub fn repeat_skipped(self) -> Cucumber<W, P, I, R, Repeat<W, Wr>, Cli> where
Wr: NonTransforming,
Re-outputs Skipped
steps for easier navigation.
Example
Output with a regular Cucumber::run()
:
Adjust Cucumber
to re-output all the Skipped
steps at the end:
MyWorld::cucumber()
.repeat_skipped()
.run_and_exit("tests/features/readme")
.await;
pub fn repeat_failed(self) -> Cucumber<W, P, I, R, Repeat<W, Wr>, Cli> where
Wr: NonTransforming,
pub fn repeat_failed(self) -> Cucumber<W, P, I, R, Repeat<W, Wr>, Cli> where
Wr: NonTransforming,
Re-outputs Failed
steps for easier navigation.
Example
Output with a regular Cucumber::fail_on_skipped()
:
MyWorld::cucumber()
.fail_on_skipped()
.run_and_exit("tests/features/readme")
.await;
Adjust Cucumber
to re-output all the Failed
steps at the end:
MyWorld::cucumber()
.repeat_failed()
.fail_on_skipped()
.run_and_exit("tests/features/readme")
.await;
Re-outputs steps by the given filter
predicate.
Example
Output with a regular Cucumber::fail_on_skipped()
:
MyWorld::cucumber()
.fail_on_skipped()
.run_and_exit("tests/features/readme")
.await;
Adjust Cucumber
to re-output all the Failed
steps ta the end by
providing a custom filter
predicate:
MyWorld::cucumber()
.repeat_if(|ev| {
use cucumber::event::{Cucumber, Feature, Rule, Scenario, Step};
matches!(
ev.as_deref(),
Ok(Cucumber::Feature(
_,
Feature::Rule(
_,
Rule::Scenario(
_,
Scenario::Step(_, Step::Failed(..))
| Scenario::Background(_, Step::Failed(..))
)
) | Feature::Scenario(
_,
Scenario::Step(_, Step::Failed(..))
| Scenario::Background(_, Step::Failed(..))
)
)) | Err(_)
)
})
.fail_on_skipped()
.run_and_exit("tests/features/readme")
.await;
Consider Skipped
Background
or regular Step
s as Failed
if their Scenario
isn’t marked with @allow.skipped
tag.
It’s useful option for ensuring that all the steps were covered.
Example
Output with a regular Cucumber::run()
:
To fail all the Skipped
steps setup Cucumber
like this:
MyWorld::cucumber()
.fail_on_skipped()
.run_and_exit("tests/features/readme")
.await;
To intentionally suppress some Skipped
steps failing, use the
@allow.skipped
tag:
Feature: Animal feature
Scenario: If we feed a hungry cat it will no longer be hungry
Given a hungry cat
When I feed the cat
Then the cat is not hungry
@allow.skipped
Scenario: If we feed a satiated dog it will not become hungry
Given a satiated dog
When I feed the dog
Then the dog is not hungry
pub fn fail_on_skipped_with<Filter>(
self,
filter: Filter
) -> Cucumber<W, P, I, R, FailOnSkipped<Wr, Filter>, Cli> where
Filter: Fn(&Feature, Option<&Rule>, &Scenario) -> bool,
pub fn fail_on_skipped_with<Filter>(
self,
filter: Filter
) -> Cucumber<W, P, I, R, FailOnSkipped<Wr, Filter>, Cli> where
Filter: Fn(&Feature, Option<&Rule>, &Scenario) -> bool,
Consider Skipped
Background
or regular Step
s as Failed
if the given filter
predicate returns true
.
Example
Output with a regular Cucumber::run()
:
Adjust Cucumber
to fail on all Skipped
steps, but the ones
marked with a @dog
tag:
MyWorld::cucumber()
.fail_on_skipped_with(|_, _, s| !s.tags.iter().any(|t| t == "dog"))
.run_and_exit("tests/features/readme")
.await;
Feature: Animal feature
Scenario: If we feed a hungry cat it will no longer be hungry
Given a hungry cat
When I feed the cat
Then the cat is not hungry
Scenario: If we feed a satiated dog it will not become hungry
Given a satiated dog
When I feed the dog
Then the dog is not hungry
And to avoid failing, use the @dog
tag:
Feature: Animal feature
Scenario: If we feed a hungry cat it will no longer be hungry
Given a hungry cat
When I feed the cat
Then the cat is not hungry
@dog
Scenario: If we feed a satiated dog it will not become hungry
Given a satiated dog
When I feed the dog
Then the dog is not hungry
Consumes already parsed cli::Opts
.
This method allows to pre-parse cli::Opts
for custom needs before
using them inside Cucumber
.
Also, any additional custom CLI options may be specified as a
clap::Args
deriving type, used as the last type parameter of
cli::Opts
.
⚠️ WARNING: Any CLI options of
Parser
,Runner
,Writer
or custom ones should not overlap, otherwisecli::Opts
will fail to parse on startup.
Example
#[derive(clap::Args)]
struct CustomCli {
/// Additional time to wait in a before hook.
#[clap(
long,
parse(try_from_str = humantime::parse_duration)
)]
before_time: Option<Duration>,
}
let cli = cli::Opts::<_, _, _, CustomCli>::parsed();
let time = cli.custom.before_time.unwrap_or_default();
MyWorld::cucumber()
.before(move |_, _, _, _| time::sleep(time).boxed_local())
.with_cli(cli)
.run_and_exit("tests/features/readme")
.await;
Feature: Animal feature
Scenario: If we feed a hungry cat it will no longer be hungry
Given a hungry cat
When I feed the cat
Then the cat is not hungry
Also, specifying --help
flag will describe --before-time
now.
Runs Cucumber
with Scenario
s filter.
Feature
s sourced from a Parser
are fed to a Runner
, which
produces events handled by a Writer
.
Example
Adjust Cucumber
to run only Scenario
s marked with @cat
tag:
MyWorld::cucumber()
.filter_run("tests/features/readme", |_, _, sc| {
sc.tags.iter().any(|t| t == "cat")
})
.await;
Feature: Animal feature
@cat
Scenario: If we feed a hungry cat it will no longer be hungry
Given a hungry cat
When I feed the cat
Then the cat is not hungry
@dog
Scenario: If we feed a satiated dog it will not become hungry
Given a satiated dog
When I feed the dog
Then the dog is not hungry
Creates a default Cucumber
executor.
-
ScenarioType
—Concurrent
by default,Serial
if@serial
tag is present on aScenario
;- Allowed to run up to 64
Concurrent
Scenario
s.
-
Writer
—Normalize
andSummarize
writer::Basic
.
impl<W, I, P, Wr, F, B, A, Cli> Cucumber<W, P, I, Basic<W, F, B, A>, Wr, Cli> where
W: World,
P: Parser<I>,
Wr: Writer<W>,
Cli: Args,
F: Fn(&Feature, Option<&Rule>, &Scenario) -> ScenarioType + 'static,
B: for<'a> Fn(&'a Feature, Option<&'a Rule>, &'a Scenario, &'a mut W) -> LocalBoxFuture<'a, ()> + 'static,
A: for<'a> Fn(&'a Feature, Option<&'a Rule>, &'a Scenario, Option<&'a mut W>) -> LocalBoxFuture<'a, ()> + 'static,
impl<W, I, P, Wr, F, B, A, Cli> Cucumber<W, P, I, Basic<W, F, B, A>, Wr, Cli> where
W: World,
P: Parser<I>,
Wr: Writer<W>,
Cli: Args,
F: Fn(&Feature, Option<&Rule>, &Scenario) -> ScenarioType + 'static,
B: for<'a> Fn(&'a Feature, Option<&'a Rule>, &'a Scenario, &'a mut W) -> LocalBoxFuture<'a, ()> + 'static,
A: for<'a> Fn(&'a Feature, Option<&'a Rule>, &'a Scenario, Option<&'a mut W>) -> LocalBoxFuture<'a, ()> + 'static,
pub fn which_scenario<Which>(
self,
func: Which
) -> Cucumber<W, P, I, Basic<W, Which, B, A>, Wr, Cli> where
Which: Fn(&Feature, Option<&Rule>, &Scenario) -> ScenarioType + 'static,
pub fn which_scenario<Which>(
self,
func: Which
) -> Cucumber<W, P, I, Basic<W, Which, B, A>, Wr, Cli> where
Which: Fn(&Feature, Option<&Rule>, &Scenario) -> ScenarioType + 'static,
Function determining whether a Scenario
is Concurrent
or
a Serial
one.
Sets a hook, executed on each Scenario
before running all its
Step
s, including Background
ones.
Sets a hook, executed on each Scenario
after running all its
Step
s, even after Skipped
of Failed
Step
s.
Last World
argument is supplied to the function, in case it was
initialized before by running before
hook or any non-failed
Step
. In case the last Scenario
’s Step
failed, we want to
return event with an exact World
state. Also, we don’t want to impose
additional Clone
bounds on World
, so the only option left is to
pass None
to the function.
Replaces Collection
of Step
s.
Runs Cucumber
with Scenario
s filter.
Feature
s sourced from a Parser
are fed to a Runner
, which
produces events handled by a Writer
.
Panics
If encountered errors while parsing Feature
s or at least one
Step
Failed
.
Example
Adjust Cucumber
to run only Scenario
s marked with @cat
tag:
MyWorld::cucumber()
.filter_run_and_exit("tests/features/readme", |_, _, sc| {
sc.tags.iter().any(|t| t == "cat")
})
.await;
Feature: Animal feature
@cat
Scenario: If we feed a hungry cat it will no longer be hungry
Given a hungry cat
When I feed the cat
Then the cat is not hungry
@dog
Scenario: If we feed a satiated dog it will not become hungry
Given a satiated dog
When I feed the dog
Then the dog is not hungry
Trait Implementations
Auto Trait Implementations
impl<W, P, I, R, Wr, Cli> RefUnwindSafe for Cucumber<W, P, I, R, Wr, Cli> where
Cli: RefUnwindSafe,
I: RefUnwindSafe,
P: RefUnwindSafe,
R: RefUnwindSafe,
W: RefUnwindSafe,
Wr: RefUnwindSafe,
<P as Parser<I>>::Cli: RefUnwindSafe,
<R as Runner<W>>::Cli: RefUnwindSafe,
<Wr as Writer<W>>::Cli: RefUnwindSafe,
impl<W, P, I, R, Wr, Cli> Send for Cucumber<W, P, I, R, Wr, Cli> where
Cli: Send,
I: Send,
P: Send,
R: Send,
W: Send,
Wr: Send,
<P as Parser<I>>::Cli: Send,
<R as Runner<W>>::Cli: Send,
<Wr as Writer<W>>::Cli: Send,
impl<W, P, I, R, Wr, Cli> Sync for Cucumber<W, P, I, R, Wr, Cli> where
Cli: Sync,
I: Sync,
P: Sync,
R: Sync,
W: Sync,
Wr: Sync,
<P as Parser<I>>::Cli: Sync,
<R as Runner<W>>::Cli: Sync,
<Wr as Writer<W>>::Cli: Sync,
impl<W, P, I, R, Wr, Cli> Unpin for Cucumber<W, P, I, R, Wr, Cli> where
Cli: Unpin,
I: Unpin,
P: Unpin,
R: Unpin,
W: Unpin,
Wr: Unpin,
<P as Parser<I>>::Cli: Unpin,
<R as Runner<W>>::Cli: Unpin,
<Wr as Writer<W>>::Cli: Unpin,
impl<W, P, I, R, Wr, Cli> UnwindSafe for Cucumber<W, P, I, R, Wr, Cli> where
Cli: UnwindSafe,
I: UnwindSafe,
P: UnwindSafe,
R: UnwindSafe,
W: UnwindSafe,
Wr: UnwindSafe,
<P as Parser<I>>::Cli: UnwindSafe,
<R as Runner<W>>::Cli: UnwindSafe,
<Wr as Writer<W>>::Cli: UnwindSafe,
Blanket Implementations
Mutably borrows from an owned value. Read more
Asserts this Writer
being Normalized
. Read more
fn fail_on_skipped_with<F>(self, f: F) -> FailOnSkipped<Self, F> where
F: Fn(&Feature, Option<&Rule>, &Scenario) -> bool,
fn fail_on_skipped_with<F>(self, f: F) -> FailOnSkipped<Self, F> where
F: Fn(&Feature, Option<&Rule>, &Scenario) -> bool,
Wraps this Writer
into a discard::Arbitrary
one, providing a
no-op ArbitraryWriter
implementation. Read more
Wraps this Writer
into a discard::Arbitrary
one, providing a
no-op FailureWriter
implementation returning only 0
. Read more