Behavior driven development
Encyclopedia
Behavior-driven development (or BDD) is an agile software development
technique that encourages collaboration between developers, QA
and non-technical or business participants in a software project. It was originally named in 2003 by Dan North as a response to test-driven development
, including acceptance test or customer test driven development practices as found in extreme programming
. It has evolved over the last few years.
On the "Agile specifications, BDD and Testing eXchange" in November 2009 in London, Dan North gave the following definition of BDD:
BDD focuses on obtaining a clear understanding of desired software behavior through discussion with stakeholders. It extends TDD
by writing test cases in a natural language that non-programmers can read. Behavior-driven developers use their native language in combination with the ubiquitous language of domain-driven design
to describe the purpose and benefit of their code. This allows the developers to focus on why the code should be created, rather than the technical details, and minimizes translation between the technical language in which the code is written and the domain language spoken by the business, users, stakeholders, project management, etc.
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.
; that is, the benefit to the business which accrues once the application is in production. The only way in which this benefit can be realized is through the user interface
(s) to the application, usually (but not always) a GUI
.
In the same way, each piece of code, starting with the UI, can be considered a stakeholder of the other modules of code which it uses. Each element of code provides some aspect of behavior which, in collaboration with the other elements, provides the application behavior.
The first piece of production code that BDD developers implement is the UI. Developers can then benefit from quick feedback as to whether the UI looks and behaves appropriately. Through code, and using principles of good design and refactoring, developers discover collaborators of the UI, and of every unit of code thereafter. This helps them adhere to the principle of YAGNI
, since each piece of production code is required either by the business, or by another piece of code already written.
In BDD, a developer or QA engineer might clarify the requirements by breaking this down into specific examples, e.g.
Note: The language of the examples below is called Gherkin and is used in cucumber for ruby
, lettuce for python , specflow for dotnet
and behat for php
.
Each scenario is an exemplar, designed to illustrate a specific aspect of behavior of the application.
When discussing the scenarios, participants question whether the outcomes described always result from those events occurring in the given context. This can help to uncover further scenarios which clarify the requirements. For instance, a domain expert noticing that refunded items are not always returned to stock might reword the requirements as "Refunded or replaced items should be returned to stock, unless faulty.".
This in turn helps participants to pin down the scope of requirements, which leads to better estimates of how long those requirements will take to implement.
The words Given, When and Then are often used to help drive out the scenarios, but are not mandated.
These scenarios can also be automated, if an appropriate tool exists to allow automation at the UI level. If no such tool exists then it may be possible to automate at the next level in, i.e.: if an MVC
design pattern has been used, the level of the Controller.
Example 1: New lists are empty
Example 2: Lists with things in them are not empty.
Both these examples are required to describe the behavior of the method, and to derive the benefit of the method. These examples are usually automated using TDD frameworks. In BDD these examples are often encapsulated in a single method, with the name of the method being a complete description of the behavior. Both examples are required for the code to be valuable, and encapsulating them in this way makes it easy to question, remove or change the behavior.
For instance, using Java
and JUnit
4, the above examples might become:
Other practitioners, particularly in the Ruby community, prefer to split these into two separate examples, based on separate contexts for when the list is empty or has items in. This technique is based on Dave Astels' practice, "One assertion per test".
Sometimes the difference between the context, events and outcomes is made more explicit. For instance:
However the example is phrased, the effect describes the behavior of the code in question. For instance, from the examples above one can derive:
The description is intended to be useful if the test fails, and to provide documentation of the code's behavior. Once the examples have been written they are then run and the code implemented to make them work in the same way as TDD. The examples then become part of the suite of regression tests.
into the code which needs it, and examples of that code's behavior are written using this object instead of the production version.
These objects can either be created by hand, or created using a mocking framework such as Mockito
, Moq, NMock
, Rhino Mocks, JMock or EasyMock.
Questioning responsibilities in this way, and using mocks to fulfill the required roles of collaborating classes, encourages the use of Role-based Interfaces. It also helps to keep the classes small and loosely coupled.
Agile software development
Agile software development is a group of software development methodologies based on iterative and incremental development, where requirements and solutions evolve through collaboration between self-organizing, cross-functional teams...
technique that encourages collaboration between developers, QA
Quality Assurance
Quality assurance, or QA for short, is the systematic monitoring and evaluation of the various aspects of a project, service or facility to maximize the probability that minimum standards of quality are being attained by the production process...
and non-technical or business participants in a software project. It was originally named in 2003 by Dan North as a response to test-driven development
Test-driven development
Test-driven development is a software development process that relies on the repetition of a very short development cycle: first the developer writes a failing automated test case that defines a desired improvement or new function, then produces code to pass that test and finally refactors the new...
, including acceptance test or customer test driven development practices as found in extreme programming
Extreme Programming
Extreme programming is a software development methodology which is intended to improve software quality and responsiveness to changing customer requirements...
. It has evolved over the last few years.
On the "Agile specifications, BDD and Testing eXchange" in November 2009 in London, Dan North gave the following definition 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.
BDD focuses on obtaining a clear understanding of desired software behavior through discussion with stakeholders. It extends TDD
Test-driven development
Test-driven development is a software development process that relies on the repetition of a very short development cycle: first the developer writes a failing automated test case that defines a desired improvement or new function, then produces code to pass that test and finally refactors the new...
by writing test cases in a natural language that non-programmers can read. Behavior-driven developers use their native language in combination with the ubiquitous language of domain-driven design
Domain-driven design
Domain-driven design is an approach to developing software for complex needs by deeply connecting the implementation to an evolving model of the core business concepts...
to describe the purpose and benefit of their code. This allows the developers to focus on why the code should be created, rather than the technical details, and minimizes translation between the technical language in which the code is written and the domain language spoken by the business, users, stakeholders, project management, etc.
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
RSpec
RSpec is a behavior driven development framework for the Ruby programming language, inspired by JBehave. It contains its own mocking framework that is fully integrated into the framework based upon JMock...
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
Cucumber (software)
Cucumber is a tool for running automated acceptance tests written in a behavior driven development style. Cucumber is written in Ruby programming language...
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.
BDD practices
The practices of BDD include:- Establishing the goals of different stakeholders required for a vision to be implemented
- Drawing out features which will achieve those goals using feature injection
- Involving stakeholders in the implementation process through outside–in software development
- Using examples to describe the behavior of the application, or of units of code
- Automating those examples to provide quick feedback and regression testingRegression testingRegression testing is any type of software testing that seeks to uncover new errors, or regressions, in existing functionality after changes have been made to a system, such as functional enhancements, patches or configuration changes....
- Using 'should' when describing the behavior of software to help clarify responsibility and allow the software's functionality to be questioned
- Using 'ensure' when describing responsibilities of software to differentiate outcomes in the scopeScope (programming)In computer programming, scope is an enclosing context where values and expressions are associated. Various programming languages have various types of scopes. The type of scope determines what kind of entities it can contain and how it affects them—or semantics...
of the code in question from side-effects of other elements of code. - Using mocksMock objectIn object-oriented programming, mock objects are simulated objects that mimic the behavior of real objects in controlled ways. A programmer typically creates a mock object to test the behavior of some other object, in much the same way that a car designer uses a crash test dummy to simulate the...
to stand-in for collaborating modules of code which have not yet been written
Outside–in
BDD is driven by business valueBusiness Value
In management, business value is an informal term that includes all forms of value that determine the health and well-being of the firm in the long-run...
; that is, the benefit to the business which accrues once the application is in production. The only way in which this benefit can be realized is through the user interface
User interface
The user interface, in the industrial design field of human–machine interaction, is the space where interaction between humans and machines occurs. The goal of interaction between a human and a machine at the user interface is effective operation and control of the machine, and feedback from the...
(s) to the application, usually (but not always) a GUI
Gui
Gui or guee is a generic term to refer to grilled dishes in Korean cuisine. These most commonly have meat or fish as their primary ingredient, but may in some cases also comprise grilled vegetables or other vegetarian ingredients. The term derives from the verb, "gupda" in Korean, which literally...
.
In the same way, each piece of code, starting with the UI, can be considered a stakeholder of the other modules of code which it uses. Each element of code provides some aspect of behavior which, in collaboration with the other elements, provides the application behavior.
The first piece of production code that BDD developers implement is the UI. Developers can then benefit from quick feedback as to whether the UI looks and behaves appropriately. Through code, and using principles of good design and refactoring, developers discover collaborators of the UI, and of every unit of code thereafter. This helps them adhere to the principle of YAGNI
You Ain't Gonna Need It
"You ain't gonna need it" is the principle in extreme programming that programmers should not add functionality until it is necessary...
, since each piece of production code is required either by the business, or by another piece of code already written.
Application examples in the Gherkin language
The requirements of a retail application might be, "Refunded or exchanged items should be returned to stock."In BDD, a developer or QA engineer might clarify the requirements by breaking this down into specific examples, e.g.
Note: The language of the examples below is called Gherkin and is used in cucumber for ruby
, lettuce for python , specflow for dotnet
and behat for php
.
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
Each scenario is an exemplar, designed to illustrate a specific aspect of behavior of the application.
When discussing the scenarios, participants question whether the outcomes described always result from those events occurring in the given context. This can help to uncover further scenarios which clarify the requirements. For instance, a domain expert noticing that refunded items are not always returned to stock might reword the requirements as "Refunded or replaced items should be returned to stock, unless faulty.".
This in turn helps participants to pin down the scope of requirements, which leads to better estimates of how long those requirements will take to implement.
The words Given, When and Then are often used to help drive out the scenarios, but are not mandated.
These scenarios can also be automated, if an appropriate tool exists to allow automation at the UI level. If no such tool exists then it may be possible to automate at the next level in, i.e.: if an MVC
Model-view-controller
Model–view–controller is a software architecture, currently considered an architectural pattern used in software engineering. The pattern isolates "domain logic" from the user interface , permitting independent development, testing and maintenance of each .Model View Controller...
design pattern has been used, the level of the Controller.
Programmer-domain examples and behavior
The same principles of examples, using contexts, events and outcomes are used to drive development at the level of abstraction of the programmer, as opposed to the business level. For instance, the following examples describe an aspect of behavior of a list:Example 1: New lists are empty
- Given a new list
- Then the list should be empty.
Example 2: Lists with things in them are not empty.
- Given a new list
- When we add an object
- Then the list should not be empty.
Both these examples are required to describe the behavior of the method, and to derive the benefit of the method. These examples are usually automated using TDD frameworks. In BDD these examples are often encapsulated in a single method, with the name of the method being a complete description of the behavior. Both examples are required for the code to be valuable, and encapsulating them in this way makes it easy to question, remove or change the behavior.
For instance, using Java
Java (programming language)
Java is a programming language originally developed by James Gosling at Sun Microsystems and released in 1995 as a core component of Sun Microsystems' Java platform. The language derives much of its syntax from C and C++ but has a simpler object model and fewer low-level facilities...
and JUnit
JUnit
JUnit is a unit testing framework for the Java programming language. JUnit has been important in the development of test-driven development, and is one of a family of unit testing frameworks collectively known as xUnit that originated with SUnit....
4, the above examples might become:
Other practitioners, particularly in the Ruby community, prefer to split these into two separate examples, based on separate contexts for when the list is empty or has items in. This technique is based on Dave Astels' practice, "One assertion per test".
Sometimes the difference between the context, events and outcomes is made more explicit. For instance:
However the example is phrased, the effect describes the behavior of the code in question. For instance, from the examples above one can derive:
- List should know when it is empty
- WindowControl should close windows
The description is intended to be useful if the test fails, and to provide documentation of the code's behavior. Once the examples have been written they are then run and the code implemented to make them work in the same way as TDD. The examples then become part of the suite of regression tests.
Using mocks
BDD proponents claim that the use of "should" and "ensureThat" in BDD examples encourages developers to question whether the responsibilities they're assigning to their classes are appropriate, or whether they can be delegated or moved to another class entirely. Practitioners use an object which is simpler than the collaborating code, and provides the same interface but more predictable behavior. This is injectedDependency injection
Dependency injection is a design pattern in object-oriented computer programming whose purpose is to improve testability of, and simplify deployment of components in very large software systems....
into the code which needs it, and examples of that code's behavior are written using this object instead of the production version.
These objects can either be created by hand, or created using a mocking framework such as Mockito
Mockito
Mockito is an open source testing framework for Java released under the MIT License. The framework allows the creation of Test Double objects called, "Mock Objects" in automated unit tests for the purpose of Test-driven Development or Behavior Driven Development .-Distinguishing Features:Mockito...
, Moq, NMock
NMock
NMock is a library of mock objects to be used in .net development for Test Driven Development. NMock is an open source project that was inspired by the JMock project. The current version as of 2011 is NMock 3.-External links:**...
, Rhino Mocks, JMock or EasyMock.
Questioning responsibilities in this way, and using mocks to fulfill the required roles of collaborating classes, encourages the use of Role-based Interfaces. It also helps to keep the classes small and loosely coupled.
External links
- Dan North's article introducing BDD
- Introduction to Behavior Driven Development
- Say Hello To Behavior Driven Development (BDD)- Part 1
- Say Hello To Behavior Driven Development (BDD)- Part 2
- Behavior Driven Development Using Ruby (Part 1)
- Behavior-Driven Development Using Ruby (Part 2)
- In pursuit of code quality: Adventures in behavior-driven development by Andrew Glover
- The RSpec Book: Behaviour Driven Development with RSpec, Cucumber, and Friends
- CBehave: A Behavior Driven Development Framework for C