In software engineering, behavior-driven development is a software development process based on
test-driven development.
Behavior-driven development combines the general techniques and principles of TDD with ideas
from domain-driven design and object-oriented analysis and design to provide software development
and management teams with shared tools and a shared process to collaborate on software
development.
Although BDD is principally an idea about how software development should be managed
by both business interests and technical insight, the practice of BDD does assume the use of
specialized software tools to support the development process.
Although these tools are often developed specifically for use in BDD projects, they can be seen
as specialized forms of the tooling that supports test-driven development.
The tools serve to add automation to the ubiquitous language that is a central theme of BDD.
History Behavior-driven development was developed
by Dan North as a response to the issues encountered teaching test-driven development:
Where to start in the process What to test and what not to test
How much to test in one go What to call the tests
How to understand why a test fails At the heart of BDD is a rethinking of the
approach to the unit testing and acceptance testing that North came up with while dealing
with these issues.
For example, he proposes that unit test names be whole sentences starting with the word
"should" and should be written in order of business value.
Acceptance tests should be written using the standard agile framework of a User story:
"As a [role] I want [feature] so that [benefit]".
Acceptance criteria should be written in terms of scenarios and implemented as classes: Given
[initial context], when [event occurs], then [ensure some outcomes].
Starting from this point, North and others developed the BDD framework over a period
of years, finally framing it as a communication and collaboration framework for developers,
QA and non-technical or business participants in a software project.
During the "Agile specifications, BDD and Testing eXchange" in November 2009 in London,
Dan North gave the following description of BDD:
BDD is a second-generation, outside-in, pull-based, multiple-stakeholder, multiple-scale, high-automation,
agile methodology.
It describes a cycle of interactions with well-defined outputs, resulting in the delivery
of working, tested software that matters.
Dan North created the first ever BDD framework, JBehave, followed by a story-level BDD framework
for Ruby called RBehave which was later integrated into the RSpec project.
He also worked with David Chelimsky, Aslak Hellesøy and others to develop RSpec and
also to write "The RSpec Book: Behaviour Driven Development with RSpec, Cucumber, and Friends".
The first story-based framework in RSpec was later replaced by Cucumber mainly developed
by Aslak Hellesøy.
In 2008, Chris Matts, who was involved in the first discussions around BDD, came up
with the idea of Feature Injection, allowing BDD to cover the analysis space and provide
a full treatment of the software lifecycle from vision through to code and release.
Principles of BDD At its core, behavior-driven development is
a specialized version of test-driven development which focuses on behavioral specification
of software units.
Test-driven development is a software development methodology which essentially states that
for each unit of software, a software developer must:
define a test set for the unit first; then implement the unit;
finally verify that the implementation of the unit makes the tests succeed.
This definition is rather non-specific in that it allows tests in terms of high-level
software requirements, low-level technical details or anything in between.
The original developer of BDD came up with the notion of BDD because he was dissatisfied
with the lack of any specification within TDD of what should be tested and how.
One way of looking at BDD therefore, is that it is a continued development of TDD which
makes more specific choices than TDD.
Behavior-driven development specifies that tests of any unit of software should be specified
in terms of the desired behavior of the unit.
Borrowing from agile software development the "desired behavior" in this case consists
of the requirements set by the business — that is, the desired behavior that has business
value for whatever entity commissioned the software unit under construction.
Within BDD practice, this is referred to as BDD being an "outside-in" activity.
Behavioural specifications Following this fundamental choice, a second
choice made by BDD relates to how the desired behavior should be specified.
In this area BDD chooses to use a semi-formal format for behavioral specification which
is borrowed from user story specifications from the field of object-oriented analysis
and design.
BDD specifies that business analysts and developers should collaborate in this area and should
specify behavior in terms of user stories, which are each explicitly written down in
a dedicated document.
Each user story should, in some way, follow the following structure:
Title: The story should have a clear, explicit title.
Narrative A short, introductory section that specifies
who is the driver or primary stakeholder of the story
which effect the stakeholder wants the story to have
what business value the stakeholder will derive from this effect
Acceptance criteria or scenarios a description of each specific case of the
narrative.
Such a scenario has the following structure: It starts by specifying the initial condition
that is assumed to be true at the beginning of the scenario.
This may consist of a single clause, or several.
It then states which event triggers the start of the scenario.
Finally, it states the expected outcome, in one or more clauses.
BDD does not have any formal requirements for exactly how these user stories must be
written down, but it does insist that each team using BDD come up with a simple, standardized
format for writing down the user stories which includes the elements listed above.
However, in 2007 Dan North suggested a template for a textual format which has found wide
following in different BDD software tools.
A very brief example of this format might look like this:
Story: Returns go to stock
In order to keep track of stock As a store owner
I want to add items back to stock when they're returned
Scenario 1: Refunded items should be returned to stock
Given a customer previously bought a black sweater from me
And I currently have three black sweaters left in stock
When he returns the sweater for a refund Then I should have four black sweaters in
stock
Scenario 2: Replaced items should be returned to stock
Given that a customer buys a blue garment And I have two blue garments in stock
And three black garments in stock.
When he returns the garment for a replacement in black,
Then I should have three blue garments in stock
And two black garments in stock
The scenarios are ideally phrased declaratively rather than imperatively — in the business
language, with no reference to elements of the UI through which the interactions take
place.
This format is referred to as the Gherkin language, which has a syntax similar to the
above example.
The term Gherkin, however, is specific to the Cucumber and JBehave software tools.
Specification as a ubiquitous language Behavior-driven development borrows the concept
of the ubiquitous language from domain driven design.
A ubiquitous language is aformal language that is shared by all members of a software
development team — both software developers and non-technical personnel.
The language in question is both used and developed by all team members as a common
means of discussing the domain of the software in question.
In this way BDD becomes a vehicle for communication between all the different roles in a software
project.
A common risk with software development includes communication breakdowns between Developers
and Business Stakeholders . BDD uses the specification of desired behavior as a ubiquitous language
for the project team members.
This is the reason that BDD insists on a semi-formal language for behavioral specification: some
formality is a requirement for being a ubiquitous language.
In addition, having such a ubiquitous language creates a domain model of specifications,
so that specifications may be reasoned about formally.
This model is also the basis for the different BDD-supporting software tools that are available.
The example given above establishes a user story for a software system under development.
This user story identifies a stakeholder, a business effect and a business value.
It also describes several scenarios, each with a precondition, trigger and expected
outcome.
Each of these parts is exactly identified by the more formal part of the language and
may therefore be processed in some way by a tool that understands the formal parts of
the ubiquitous language.
Specialized tooling support Much like test-driven design practice, behavior-driven
development assumes the use of specialized support tooling in a project.
Inasmuch as BDD is, in many respects, a more specific version of TDD, the tooling for BDD
is similar to that for TDD, but makes more demands on the developer than basic TDD tooling.
Tooling principles In principle a BDD support tool is a testing
framework for software, much like the tools that support TDD.
However, where TDD tools tend to be quite free-format in what is allowed for specifying
tests, BDD tools are linked to the definition of the ubiquitous language discussed earlier.
As discussed, the ubiquitous language allows business analysts to write down behavioral
requirements in a way that will also be understood by developers.
The principle of BDD support tooling is to make these same requirements documents directly
executable as a collection of tests.
The exact implementation of this varies per tool, but agile practice has come up with
the following general process: The tooling reads a specification document.
The tooling directly understands completely formal parts of the ubiquitous language.
Based on this, the tool breaks each scenario up into meaningful clauses.
Each individual clause in a scenario is transformed into some sort of parameter for a test for
the user story.
This part requires project-specific work by the software developers.
The framework then executes the test for each scenario, with the parameters from that scenario.
Dan North has developed a number of frameworks that support BDD, whose operation is based
on the template that he suggested for recording user stories.
These tools use a textual description for use cases and several other tools have followed
suit.
However, this format is not required and so there are other tools that use other formats
as well.
For example Fitnesse, has also been used to roll out BDD.
Tooling examples There are several different examples of BDD
software tools in use in projects today, for different platforms and programming languages.
Possibly the most well-known is JBehave, which was developed by Dan North.
The following is an example taken from that project:
Consider an implementation of the Game of Life.
A domain expert might want to specify what should happen when someone is setting up a
starting configuration of the game grid.
To do this, he might want to give an example of a number of steps taken by a person who
is toggling cells.
Skipping over the narrative part, he might do this by writing up the following scenario
into a plain text document:
Given a 5 by 5 game When I toggle the cell at
Then the grid should look like .....
..... .....
..X..
..... When I toggle the cell at
Then the grid should look like .....
..... .....
..X..
When I toggle the cell at Then the grid should look like
..... .....
..X..
The bold print is not actually part of the input; it is included here to show which words
are recognized as formal language.
JBehave recognizes the terms Given, When and Then.
Based on this, JBehave is capable of reading the text file containing the scenario and
parsing it into clauses.
JBehave then takes these clauses and passes them on to code that is capable of setting
a test, responding to the event triggers and verifying the outcome.
This code must be written by the developers in the project team.
In this case, the code might look like this:
The code has a method for every type of clause in a scenario.
JBehave will identify which method goes with which clause through the use of annotations
and will call each method in order while running through the scenario.
The text in each clause in the scenario is expected to match the template text given
in the code for that clause.
JBehave supports the matching of actual clauses to templates and has built-in support for
picking terms out of the template and passing them to methods in the test code as parameters.
The test code provides an implementation for each clause type in a scenario which interacts
with the code that is being tested and performs an actual test based on the scenario.
In this case: The theGameIsRunning method reacts to a Given
clause by setting up the initial game grid.
The iToggleTheCellAt method reacts to a When clause by firing off the toggle event described
in the clause.
The theGridShouldLookLike method reacts to a Then clause by comparing the actual state
of the game grid to the expected state from the scenario.
The primary function of this code is to be a bridge between a text file with a story
and the actual code being tested.
Note that the test code has access to the code being tested and is very simple in nature.
Finally, in order to run the tests, JBehave requires some plumbing code that identifies
the text files which contain scenarios and which inject dependencies into the test code.
This plumbing code is not illustrated here, since it is a technical requirement of JBehave
and does not relate directly to the principle of BDD-style testing.
Story versus specification A separate subcategory of behavior-driven
development is formed by tools that use specifications as an input language rather than user stories.
An example of this style is the RSpec tool that was also developed by Dan North.
Specification tools don't use user stories as an input format for test scenarios but
rather use functional specifications for units that are being tested.
These specifications often have a more technical nature than user stories and are usually less
convenient for communication with business personnel than are user stories.
An example of a specification for a stack might look like this:
Specification: Stack
When a new stack is created Then it is empty
When an element is added to the stack Then that element is at the top of the stack
When a stack has N elements And element E is on top of the stack
Then a pop operation returns E And the new size of the stack is N-1
Such a specification may exactly specify the behavior of the component being tested, but
is less meaningful to a business user.
As a result, specification-based testing is seen in BDD practice as a complement to story-based
testing and operates at a lower level.
Specification testing is often seen as a replacement for free-format unit testing.
Specification testing tools like RSpec and JDave are somewhat different in nature from
tools like JBehave.
Since they are seen as alternatives to basic unit testing tools like JUnit, these tools
tend to favor forgoing the separation of story and testing code and prefer embedding the
specification directly in the test code instead.
For example, an RSpec test for a hashtable might look like this:
This example shows a specification in readable language embedded in executable code.
In this case a choice of the tool is to formalize the specification language into the language
of the test code by adding methods named it and should.
Also there is the concept of a specification precondition – the before section establishes
the preconditions that the specification is based on.
The result of test will be:
Hash should eq {}
includes key hashes the correct information in a key
See also Jasmine
Cucumber Behat
References
External links Dan North's article introducing BDD
Say Hello To Behavior Driven Development- Part 1
Say Hello To Behavior Driven Development- Part 2
Behavior Driven Development Using Ruby Behavior-Driven Development Using Ruby
In pursuit of code quality: Adventures in behavior-driven development by Andrew Glover
The RSpec Book: Behaviour Driven Development with RSpec, Cucumber, and Friends
ScalaTest: Tests as specifications Unit test JavaScript applications with Jasmine
Chai BDD/TDD Javascript Library Assertion Styles
Choosing a BDD framework for .NET