Next: (veritas cli), Previous: (veritas assert), Up: API
Behaviour-driven (Given/When/Then) helpers for Veritas, in the spirit of Cucumber/Gherkin scenarios. A scenario is a suite whose steps are ordinary tests, so every existing reporter, filter and runner feature keeps working. Step names are prefixed with their keyword so the output reads naturally.
Steps run in order by default: scenarios disable shuffling and concurrency so that Given -> When -> Then always executes sequentially.
State is shared between steps simply by closing over a ‘let’ binding in the scenario body, for example:
(scenario "withdrawing too much" (let ((account (make-account 100))) (given "an account with 100" (assert-equal #:expect 100 #:got (account-balance account))) (when-step "withdrawing 150" (assert-false (withdraw account 150))) (then "the balance is unchanged" (assert-equal #:expect 100 #:got (account-balance account)))))
Latin aliases are provided for those who prefer them: fabula/scaena for scenario, dato for given, quando for when, tunc for then, etiam for and, and sed for but.
The three steps also have PascalCase aliases – Given, When and Then – for readers who expect the keywords to look like the Cucumber ones.
The When step is called ‘when-step’ rather than ‘when’ because Guile’s core ‘when’ is a syntax keyword and importing a conflicting binding would break ‘(when ...)’ for every module that imports Veritas BDD. The Latin ‘quando’ is unshadowed and reads naturally.
Define a Given (setup) step named name.
Define a Then (outcome) step named name.
Define a When (action) step named name.
Called when-step rather than when so it does not shadow
Guile’s when syntax.
Define an And (continuation) step named name.
Define a But (continuation) step named name.
Define a Given (setup) step named name.
Define an And (continuation) step named name.
Define a Given/When/Then scenario named name.
A scenario is a suite, so its steps run in declaration order. Keywords
are forwarded to suite, and steps come from given,
when-step, then, and-step and but-step.
timeout, when given, caps the whole scenario in seconds, exactly
like suite; a step can carry its own #:timeout as well,
since steps are ordinary tests.
(scenario "emptying the cart"
(given "a cart with one item"
(assert-equal #:expect 1 #:got (cart-size cart)))
(when-step "the cart is emptied"
(empty-cart! cart))
(then "the cart is empty"
(assert-true (cart-empty? cart))))
Define a Given/When/Then scenario named name.
A scenario is a suite, so its steps run in declaration order. Keywords
are forwarded to suite, and steps come from given,
when-step, then, and-step and but-step.
timeout, when given, caps the whole scenario in seconds, exactly
like suite; a step can carry its own #:timeout as well,
since steps are ordinary tests.
(scenario "emptying the cart"
(given "a cart with one item"
(assert-equal #:expect 1 #:got (cart-size cart)))
(when-step "the cart is emptied"
(empty-cart! cart))
(then "the cart is empty"
(assert-true (cart-empty? cart))))
Define a Given (setup) step named name.
Define a When (action) step named name.
Called when-step rather than when so it does not shadow
Guile’s when syntax.
Define a Given/When/Then scenario named name.
A scenario is a suite, so its steps run in declaration order. Keywords
are forwarded to suite, and steps come from given,
when-step, then, and-step and but-step.
timeout, when given, caps the whole scenario in seconds, exactly
like suite; a step can carry its own #:timeout as well,
since steps are ordinary tests.
(scenario "emptying the cart"
(given "a cart with one item"
(assert-equal #:expect 1 #:got (cart-size cart)))
(when-step "the cart is emptied"
(empty-cart! cart))
(then "the cart is empty"
(assert-true (cart-empty? cart))))
Define a Given/When/Then scenario named name.
A scenario is a suite, so its steps run in declaration order. Keywords
are forwarded to suite, and steps come from given,
when-step, then, and-step and but-step.
timeout, when given, caps the whole scenario in seconds, exactly
like suite; a step can carry its own #:timeout as well,
since steps are ordinary tests.
(scenario "emptying the cart"
(given "a cart with one item"
(assert-equal #:expect 1 #:got (cart-size cart)))
(when-step "the cart is emptied"
(empty-cart! cart))
(then "the cart is empty"
(assert-true (cart-empty? cart))))
Define a But (continuation) step named name.
Define a Given/When/Then scenario named name.
A scenario is a suite, so its steps run in declaration order. Keywords
are forwarded to suite, and steps come from given,
when-step, then, and-step and but-step.
timeout, when given, caps the whole scenario in seconds, exactly
like suite; a step can carry its own #:timeout as well,
since steps are ordinary tests.
(scenario "emptying the cart"
(given "a cart with one item"
(assert-equal #:expect 1 #:got (cart-size cart)))
(when-step "the cart is emptied"
(empty-cart! cart))
(then "the cart is empty"
(assert-true (cart-empty? cart))))
Define a Then (outcome) step named name.
Define a Then (outcome) step named name.
Define a When (action) step named name.
Called when-step rather than when so it does not shadow
Guile’s when syntax.
Next: (veritas cli), Previous: (veritas assert), Up: API