First, BDD should not be used instead of TDD. As Dan
North explained it, with BDD you specify the behaviour
looking at the system from the ouside.
When you then implement the stuff and get "deeper" into
the code you will use your TDD skills as usual.
BDD should be used to connect developers and business
people, imho this is where the main benefit of BDD is,
you dont need a framework for that but we develeopers
can't help it, when things are organised we think "hey,
I can implement this in code" :) The BDD frameworks only
add another benefit, an executable spec.
If both "camps" can speak in terms of Given/When/Then
with each other about the features to implement they
will connect better.
And finally, I don't really get why it should be
unreadable in VB.NET?
The story would look something like:
Story("Transfer to cash account"). _
AsA("Bank card holder"). _
IWant("to transfer money from my savings account"). _
SoThat("I can get cash easily from an ATM")
That is a lot of great feedback! Joe and I have had a
few conversations about many of the points you've
brought up. Behave# is still in its infancy, so
questions like these will definitely help in shaping its
role and direction. We're going to release a vision
statement soon that should hopefully clarify the purpose
and scope of Behave#. Thanks again for the feedback!
Morgan's comment almost answers the question on when to
use BDD versus TDD: To me, BDD is about capturing use
cases/stories in an automatable, repeatable fashion.
If you look at a typical componentized ('layered')
application architecture, it only makes sense to apply
BDD to components that are very close to the application
perimeter: UI Controllers/Façades/etc. Such components
typically exist for the one purpose of wiring up an
external interface (UI/Service Interface) to the rest of
the application, so they most closely resemble the
business needs.
One of the tricky parts of software development
(particularly OOD) is decomposing all the different
concerns of an application into autonomous units. While
doing that, we also create a level of abstraction (data
access components, interfaces, logging strategies, what
have you) that removes most of the code quite far from
the business requirements.
As such, unit testing is the only sort of test that
makes sense at that level, since you can't map a
business requirement entirely to any single component.
This means that in essense, a behavioral test is a sort
of integration test.
In agile projects, this approach is still valuable,
since we should never write code for which there is no
business requirement. You could actually take this
further and enable code coverage on your behavioral
tests: If you have code that's not covered, you either
need to write a test, or that code should not be there.
That may sound familiar to anyone used to TDD, but the
difference is that 'normal' unit tests don't count: Only
behavioral tests count towards 'requirments coverage'.
That's probably taking things a bit too far, but it's an
intriguing idea :)
While I agree with the distinction that was discussed
above, there is something to be said regarding
abstraction in the developer realm.
BDD allows you to specify how the system should behave.
It's use is customer facing. But wouldn't you want the
developer to also use this as an abstraction? Fluent
interface is already in use in NUnit, making the tests
more readable. Why not take the next step (I know it
looks like sci-fi today) and abstract the component (or
service provider) with similar taxonomy?
If we leave APIs out of the discussion, we are talking
about two languages (DevSpeak and CustomerSpeak) that
may someday, with the right tools converge.