Introducing Behave#


This post was originally published here.

I really like the idea of executable requirements.  Executable requirements is the idea that I can express requirements from the business in a human-readable, executable format.  Part of fulfilling the requirement is that the “executable requirement” part can execute successfully in the form of acceptance tests.

Recently, I checked out a couple of API’s for executable requirements in the form of behavior-driven design (BDD).  For more information on BDD, check out these articles from Dan North’s blog:

  • Introducing BDD
    • What’s in a Story?</ul> The API’s I checked out were NBehave and Joe Ocampo’s NUnit.Behave.  NBehave was rather cumbersome to set up, and didn’t have much of a fluent interface.  NUnit.Behave was much easier to use, but forced a dependency on NUnit.  I didn’t want to be forced to use NUnit, nor did I want to inherit from certain classes or implement certain interfaces.  Heavily influenced by NUnit.Behave, I created Behave#.

    What is Behave#?

    Behave# (http://www.codeplex.com/BehaveSharp) is a fluent interface to express executable requirements in the form of acceptance tests with a distinct BDD grammar.  Stories follow the “As a I want so that ” template.  Stories are made up of scenarios, which follow the “Given When Then” template.  Through a fluent interface, Behave# shapes your acceptance tests to closely match the original user story.

    What would a user story look like in code?

     The fluent interface I settled on looks like:

    new Story("Transfer to cash account")
    .AsA("savings account holder")
    .IWant("to transfer money from my savings account")
    .SoThat("I can get cash easily from an ATM")
    
    .WithScenario("Savings account is overdrawn")
    
        .Given("my savings account balance is", -20)
            .And("my cash account balance is", 10)
        .When("I transfer to cash account", 20)
        .Then("my savings account balance should be", -20)
            .And("my cash account balance should be", 10);
    

</pre> </div>

I really like this syntax as it can be read very easily and there aren&#8217;t a lot of other objects or frameworks getting in the way.&nbsp; So how do we actually execute custom actions in our story definition?&nbsp; Here&#8217;s a full-fledged example, using NUnit to provide assertions:

<div class="CodeFormatContainer">
  <pre>[Test] <span class="kwrd">public</span> <span class="kwrd">void</span> Transfer_to_cash_account() {

Account savings = <span class="kwrd">null</span>;
Account cash = <span class="kwrd">null</span>;

Story transferStory = <span class="kwrd">new</span> Story(<span class="str">"Transfer to cash account"</span>);

transferStory
    .AsA(<span class="str">"savings account holder"</span>)
    .IWant(<span class="str">"to transfer money from my savings account"</span>)
    .SoThat(<span class="str">"I can get cash easily from an ATM"</span>);

transferStory
    .WithScenario(<span class="str">"Savings account is in credit"</span>)

        .Given(<span class="str">"my savings account balance is"</span>, 100, <span class="kwrd">delegate</span>(<span class="kwrd">int</span> accountBalance) { savings = <span class="kwrd">new</span> Account(accountBalance); })
            .And(<span class="str">"my cash account balance is"</span>, 10, <span class="kwrd">delegate</span>(<span class="kwrd">int</span> accountBalance) { cash = <span class="kwrd">new</span> Account(accountBalance); })
        .When(<span class="str">"I transfer to cash account"</span>, 20, <span class="kwrd">delegate</span>(<span class="kwrd">int</span> transferAmount) { savings.TransferTo(cash, transferAmount); })
        .Then(<span class="str">"my savings account balance should be"</span>, 80, <span class="kwrd">delegate</span>(<span class="kwrd">int</span> expectedBalance) { Assert.AreEqual(expectedBalance, savings.Balance); })
            .And(<span class="str">"my cash account balance should be"</span>, 30, <span class="kwrd">delegate</span>(<span class="kwrd">int</span> expectedBalance) { Assert.AreEqual(expectedBalance, cash.Balance); })

        .Given(<span class="str">"my savings account balance is"</span>, 400)
            .And(<span class="str">"my cash account balance is"</span>, 100)
        .When(<span class="str">"I transfer to cash account"</span>, 100)
        .Then(<span class="str">"my savings account balance should be"</span>, 300)
            .And(<span class="str">"my cash account balance should be"</span>, 200)

        .Given(<span class="str">"my savings account balance is"</span>, 500)
            .And(<span class="str">"my cash account balance is"</span>, 20)
        .When(<span class="str">"I transfer to cash account"</span>, 30)
        .Then(<span class="str">"my savings account balance should be"</span>, 470)
            .And(<span class="str">"my cash account balance should be"</span>, 50);

transferStory
    .WithScenario(<span class="str">"Savings account is overdrawn"</span>)

        .Given(<span class="str">"my savings account balance is"</span>, -20)
            .And(<span class="str">"my cash account balance is"</span>, 10)
        .When(<span class="str">"I transfer to cash account"</span>, 20)
        .Then(<span class="str">"my savings account balance should be"</span>, -20)
            .And(<span class="str">"my cash account balance should be"</span>, 10);

}

</pre> </div>

To perform actions with each &#8220;Given When Then&#8221; fragment, I pass in a delegate (anonymous in this case, but much prettier with lambda expressions in C# 3.0).&nbsp; This delegate is executed as the story execution proceeds, and&nbsp;is cached by name, so each time the story sees &#8220;my cash account balance is&#8221;, it will execute the appropriate delegate.&nbsp; I don&#8217;t need to define the custom action every time.

The result of the execution is the story results outputted in a human readable format (by default, to Debug):

<div class="CodeFormatContainer">
  <pre>Story: Transfer to cash account

Narrative: As a savings account holder I want to transfer money from my savings account So that I can get cash easily from an ATM

Scenario 1: Savings account is in credit Given my savings account balance is: 100 And my cash account balance is: 10 When I transfer to cash account: 20 Then my savings account balance should be: 80 And my cash account balance should be: 30

  Given my savings account balance is: 400
     And my cash account balance is: 100
  When I transfer to cash account: 100
  Then my savings account balance should be: 300
     And my cash account balance should be: 200

  Given my savings account balance is: 500
     And my cash account balance is: 20
  When I transfer to cash account: 30
  Then my savings account balance should be: 470
     And my cash account balance should be: 50

Scenario 2: Savings account is overdrawn Given my savings account balance is: -20 And my cash account balance is: 10 When I transfer to cash account: 20 Then my savings account balance should be: -20 And my cash account balance should be: 10</pre> </div>

This format closely resembles the original user story I received from the business.

### Conclusion

I like being able to verify deliverables in the form of automated tests.&nbsp; When these tests closely resemble the original requirements as user stories, I&#8217;m more confident in the deliverables.&nbsp; Having executable requirements in the form of acceptance tests in a fluent interface that matches the original requirements can bridge the gap between what the business asks for and what gets delivered.&nbsp; [Behave#](http://www.codeplex.com/BehaveSharp) gets us one step closer to bridging that gap.
When Technical Debt leads to bankruptcy