[Rspec-devel] Given,Then,When

David Chelimsky dchelimsky at gmail.com
Wed Aug 9 10:28:35 EDT 2006


Fellow rspec'ers:

One thing lacking in the current rspec syntax is direct support of the
BDD triad: Given,When,Then. Right now, rspec supports Given in the
form of contexts and combines When and Then in specify blocks. This
lends itself well to structural aspects of the code we're specifying
(i.e. "A standard deck of cards should have 52 cards", but does not do
a good job of separating out events (When) from expected outcomes
(Then).

In addition to better alignment w/ BDD-speak, separating out the Then
from the When would also support things like using the expectations to
drive documentation when there is only one expectation in the "then"

behavior_of "A mug" do
  given "an empty mug" do
    @mug = Mug.new
    @bartender = Bartender.new
  end
  when "the bartender is finished pouring beer into it" do
    @bartender.pour_beer_into @mug
  end
  then do
    @mug.should_be_full
  end
end

producing something like:

Given an empty mug
When the bartender is finished pouring beer into it
Then mug should be full

If you want that to read "Then the mug should be full" (adding "the"
for readability), you could always pass a string to the method, but
this would mean that you wouldn't have to, eliminating some of the
duplication between documentation and code.

This could possibly work for mocks as well. Because we have control
over the various blocks, we might be able to reverse execution order
when mocks are involved. This would allow us to keep the expectations
at the end when mocks are used (rather than setting them in advance),
preserving the Given,When,Then format!

behaviour_of "A deck of cards" do
  given "A freshly shuffled deck" do
    @deck = Deck.new
    @deck.shuffle
    @first_hand = mock("hand")
    @second_hand = mock("hand")
  end
  when "asked to deal a standard poker hand" do
    @deck.deal [@hand]
  end
  then "the hand should receive five cards" do
    @hand.should_receive(:add_card).exactly(5).times
  end
end

Thoughts?

David


More information about the Rspec-devel mailing list