We've had test automation in one form or another for decades - but it was almost always done by a test-automator alone. When the results of the test did not match what the automator expected, the programmer and tester had to argue about who was "right"; then bring in the product manager to have the same conversation again. BDD prevents problems by thinking of the behavior as examples, and having (at least) all three roles represented when defining the examples.
Here's how it works: Before any programming begins on a story, everyone gets together to talk about what the customer wants in the next release and how a new set of features will add value to the product. After this, development goes off to make product and occasionally deliver testable bits. If they have time, the product group occasionally checks in on what is being created while working with customers on what they might want next. Usually though, their focus is on the next release.
That means that for each story (or feature or requirement) a small group gets together to acceptance criteria (some call this "rejection criteria", which we'll explain later) for that feature. The flow of work potentially changes from business -> development -> test to something where the three groups all work together until a feature is shippable.
If test results are made public using a wiki or a CI system, then the product team can have a constant feel for how far along a feature is in development.
Almost Natural Language
The classic way to describe tests in BDD is to put then in the form of Given, When, Then. Given describes the current system state or a set of preconditions for a test. When is the behavior or set of test steps that your test will perform. Then is where assertions, or the expected changes from your test, are described. The outline of a test is done in something very close to English, which might look like this:
GIVEN I am in a Amazon.com cart with 1 copy of The Shape of Actions WHEN I apply a 10 percent discount code THEN Total = total - (total * 0.10)
This part of the test would probably be written by a product manager or maybe a non-technical tester. Interpreters can't work with English though, code has to be written to make that set of descriptions useful, so the roles gather to create the code above, which is actually in Gherkin, a programmable language. After the meeting the programmer can write the ruby (or Java, or .net) code that the Gherkin will call.
Rather than calling something in this format a test, people that do BDD call this a scenario or a specification. Behavior Driven Development is not a testing technique. Testing is part of a product strategy that can help to discover quality related information that might affect the future of the product. BDD on the other hand, is a development strategy, or maybe a product management strategy if you look at it through the right lens. It acts as a reminder to developers about the value of what they are building and helps them to build the right thing the first time around. (The automated checks that remain after BDD is done can be part of a strong risk management strategy.)
The last few years have seen an explosion in BDD frameworks -- RSPEC, EasyB, JBehave, and by far the most popular is Cucumber. Popularity comes with the benefit of lots of support in the form of language bindings, integrations, and help resources like books, user groups, and conferences. There are Cucumber implementations in just about every language you would care about like Java, Ruby, and PHP.
It is Cucumber in particular that is know for Gherkin. Gherkin is the engine behind the scenes that makes it possible to use a human readable format to create tests. Using tags in the Gherkin file, code written in the Cucumber framework works to perform that set of behaviors.
Regardless of how simple things seem externally, there are still layers of frameworks and code that make the tool and checks come together.
Something To Think About
Even though BDD frameworks can create a nice middle ground between technical staff and the business units, there are a few things to be aware of. Behavior Driven Development is often used to create a set of acceptance tests. The big gamble is that the product should be releasable as soon as all of these tests pass. Given/When/Then tests check only the "then" condition, and assume "... and nothing else bad happens." That can be a big assumption to make.
I like to flip the idea on its side, and think of BDD as rejection criteria. That is to say, while a failing test guarantees the software is not ready to ship, but a passing test does not mean the product is ready to release.
Also, keep in mind that BDD scenarios tend to be dead simple. They begin with a specific system state and then perform simple operations in the same order ever time. Something like navigate to amazon.com, add the book Tacit and Explicit Knowledge to your cart, and then verify that the book is in your cart along with all the appropriate information.
A normal user might do something more along the lines of searching for a book, reading the reviews, adding the book to the cart but accidentally adding 2 copies instead of 1, leaving the cart to browse more before returning to the cart to see that the wrong number was added, and finally changing the quantity so that there is only one copy. Even this is probably a simple example that ignores everything a person does while trying to buy a book on amazon.
Be careful not to get lulled into a false sense of comfort from reports saying all the checks pass. You will probably want to know more before making important decisions like when to ship.
Today we've just barely scratched the surface on BDD and a few key benefits, and considerations. The next step is to try a small experiment with your team to see if this style of development can add value. Also, check out our latest piece on Test-Driven Development.