An Introduction To Test-Driven Development (TDD)

Download as pptx, pdf, or txt
Download as pptx, pdf, or txt
You are on page 1of 30

An Introduction to

Test-Driven Development (TDD)

Agenda
5 minutes

30 minutes

1.

What is TDD?

2.

TDD Stages

3.

How do we get started in TDD?

4.

Why TDD?

What is TDD?

TDD is a technique whereby you write your test cases


before you write any implementation code

Initially, the developer writes a failing automated test case


that defines the new function, then produces code to pass
that test.

An indication of intent
Tests provide a specification of what a piece of code actually
does
Some might argue that tests are part of the documentation

TDD Stages
Write a test

Refactor code
(and test)

Compile

Run test,
watch it pass

Fix compile errors

Write code

Run test,
watch it fail

TDD starts from User Stories

Start from writing acceptance tests. This is a natural


TDD approach.

Before TDD

After TDD

ID: US18898
Name: Remove Recurring Flag in the agreement
screens in Siebel
Description:
As a GCSO Rep, I want to see clean and accurate
contract data in Siebel, so I can perform my work
correctly, Since the Recurring Flag is being "retired" in
favor of other contract characteristics like Contract
Term, Billing Behavior and Renewal Term / UOM, the
Agreement Recurring Flag should be removed from all
Siebel UI's where it is displayed.

ID: US18898
Name: Remove Recurring Flag in the agreement
screens in Siebel

Also I would like the "contracts" pulled down and a


new header "Contract Details" put above.
Acceptance:
Agreement Screens do not display Recurring Field.
Contracts pulled down
New heading of "contract details" added above.

Acceptance test:
The system will display clean, accurate contract data
in Siebel:
Contracts pulled down
Contract Details in header
Description:
As a GCSO Rep, I want to see clean and accurate
contract data in Siebel, so I can perform my work
correctly, Since the Recurring Flag is being "retired" in
favor of other contract characteristics like Contract
Term, Billing Behavior and Renewal Term / UOM, the
Agreement Recurring Flag should be removed from all
Siebel UI's where it is displayed.

TDD ends with an adjusted Definition of Done

In a TDD environment, the definition of "done" is pretty simple:


All automated tests pass
Those automated tests should include new ones written for
the story in question to verify the required functionality or
behavior exists and works.
Code review passed
At least one senior dev on the team is content to let your
work become part of the codebase, and that you didn't
"cheat" or "hack" your way through the story.
Commit successful
Includes the build bot passing all automated tests, code
coverage metrics, style cop checks, etc.

Why TDD? What are the agile benefits?

Bob Martin:

The act of writing a unit test is more an act


of design than of verification

Confidence boost

By practicing TDD, developers will strive to


improve their code without the fear that is
normally associated with code changes

Isnt the green bar a feel good factor?

Remove / Reduce reliance on the


debugger

No more debug-later attitudes

5 Steps to get to TDD:


Specifics you can take back to your teams
1.

Pick 1 feature to pilot TDD. Make sure theres a clear team


understanding of its requirements and decomposition.
Groom the new user stories together.

2.

Have each developer create a test as if code already


existed. Run the tests as a group. They should fail.

3.

Make the test pass by any means necessary. Write the

production code to make the test pass by keeping it simple.


4.

Refactor. Remove duplication caused by the addition of new


functionality. Rerun all the tests to make sure they still pass.

5.

Repeat. Each cycle should be short. A typical work hour


usually contains 3 4 cycles.

Summary

TDD does not replace traditional testing

It defines a proven way that ensures effective unit testing


Tests are working examples of how to invoke a piece of code

Essentially provides a working specification for the code

No code should go into production unless it has associated


tests

Catch bugs before they are shipped to your customer

No code without tests

Tests determine, or dictate, the code


9

Managing the change to TDD

Project Management

Communications

Key messages and key themes inform, engage and promote sustained change.

Training

Set the guiding principles that endorse TDD.

TDD is a new behavior. It is key to define and provide your team with helpful
resources such as quick reference guides, demos, and coaching.

Common sense and innovation

You know your team culture best. Dont go by the book on TDD methods. If
your teams get engaged by using a buddy system, or learn better by getting
outside, sponsor an event to get them moving.

10

The Guiding Principles to TDD


1.

Dont kill the messenger

2.

Make every requirement testable

3.

Anticipate some failure by making room for correction

4.

Embrace learning

5.

Avoid isolation

11

An Introduction to
Behaviour Driven Development
(BDD)

Behavior driven development


BDD is not:

A testing framework or style of testing

A method for writing tests

BDD is:

A formalised template for User Stories

Able to create testable User Stories since they are defined in a


formal manner

Promotes security to a first call citizen in the analysis process

Behavior driven

How do you write a test when you dont know where you are going?

Maybe we need requirements that are easy to write tests for?

Requirements
What are they

Describes what a system should do but not how it will be done

Contract between the implementation team and the analysis team

Audience is typically the stake holders and not the development team

Requirements Precise and clear over verbose


We want requirements that

Can be tested!!!

Are attainable!!!

Are traceable into code!!!

Requirements gathering
BDD merges two different approaches

User Stories
Short one or two line statement that maps to a few days of development work
Highly focused

Domain Driven Design


Ubiquitous language Ensure business terminology permeates into code
Clear single definition (within the project) for each business concept - Account has a single
meaning

BDD User Stories


Formal template for User Stories

Story Template
As a [User/Role]
I want [Behaviour]
so that [I receive benefit]
Example
As a Operations staff member
I want To create a Portfolio
so that So that it can be traded

BDD User Stories

Formal template for User Stories


Scenario Template
Given some initial context (the givens),
When an event occurs,
then ensure some outcomes.
Example
Given New portfolio is called Balanced Fund
When Portfolio already exists
then Portfolio can not be created

NBehave
What is it?

.NET Library for writing automated BDD style tests

Fluent syntax for building up a BDD Style User Stories

Test runner that executes the stories and generates a report listing the contents of the stories

BSD License

Creating a BDD Theme


Collection of related stories
[Theme("Portfolio Maintenance")]
public class PortfolioMaintenanceStory
{
[Story]
public void portfolio_create_story () { ... }
[Story]
public void portfolio_delete_story() { ... }
}
Reference: NBehave.Narrator.Framework.dll

Creating a Story
Fluent interface to define the story

var story = new Story("Create portfolio");


story.AsA(Operations team member")
.IWant("To create a new portfolio on behalf of a portfolio manager")
.SoThat("the portfolio manager can configure the portfolio and the front office can
trade");

Creating a Scenario
Fluent interface to define the story

story.WithScenario("portfolio does not exist")


.Given("portfolio name is $name", "Aggressive Fund")
.When("portfolio does not exist in the database")
.Then("new portfolio should be created");

story.WithScenario("portfolio already exists")


.Given("portfolio name is $name", "Aggressive Fund")
.When("portfolio already exists in database")
.Then("an error should occur");

Executing the test


With NBehave runner or mbUnit

Ouch we get an error???

The scenario throws an exception NBehave isnt validating any code

Use Pending
story.WithScenario("portfolio does not exist")
.Pending("In progress")
.Given("portfolio name is $name", "Aggressive Fund")
.When("portfolio does not exist in the database")
.Then("new portfolio should be created");

Behavior Driven Development

1.
2.
3.
4.
5.

Across the Project (Story) Life Cycle

Story
Pending Scenario
Stubbed Behavior Cycle (Red, Green, Refactor)
Real Behavior Cycle (Red, Green, Refactor)
Acceptance Test

Story

Pending
Scenario

Stubbed
Scenario

Real
Behaviour

Acceptance
Test

Stubbing out the behavior


With NBehave and Rhino. Mocks
Steps to generate an API
1. Go through the User story and find all the domain objects
2. Create a class for each domain object but dont add state
3. Go through the User story and create a find all the services that are required
(Repositories etc)
4. Create an interface for each service but dont add any methods
5. Slowly implement the story
6. Add domain object properties as required
7. Add methods signatures as required
8. Use Stubs to explore Inputs/Outputs to the methods

Stubbing example - Create a new portfolio story


string portfolioName = "";
Portfolio p = null;
var portfolioRepository = MockRepository.GenerateStub<IPortfolioRepository>();
var portfolioService = MockRepository.GenerateStub<IPortfolioService>();

s.WithScenario("portfolio already exists")


.Given("portfolio name is $name", "Aggressive Fund", n => {
portfolioName = n;
p = new Portfolio { Name = portfolioName };
portfolioRepository.
Stub(x => x.FindPortfolioByName(portfolioName)).Return(p);
portfolioService.
Stub(X => X.CreatePortfolio(p)).Throw(new
})

ItemExistsException());

Stubbing example
Create a new portfolio story

.When("portfolio already exists in database",


() => Assert.IsNotNull(
portfolioRepository.FindPortfolioByName(portfolioName))
)
.Then("new portfolio create should fail",
() => Assert.Throws<ItemExistsException>(() =>
portfolioService.CreatePortfolio(p))
);

TFD/BDD Comparison
Test First

Behavior Driven

Bottom Up approach
Lots of little steps working towards a
solution

Output
Tests

Top down approach


Design starting with interfaces (using
stubs)
Back fill with code later

Output
API creation

Giving it a go
Adding NBehave to your team

Developer Driven

Story as Pseudo code

Peer programming One person writes the scenario the other person removes
Pending() and makes it green

Dont use specification syntax

Consider not using NBehave story runner and host Stories within current
Continuous Integration setup (Use NUnit Test Fixture as opposed to Theme)

Giving it a go
Adding NBehave to your team

continued...

Scrum Master/PM driven

Ask for detailed requirements in BBD style

Embedded BDD Lifecycle (API->Stubs->Implementation->UAT) into estimates/deliverables

Use NBehave story output as a deliverable to analysis/test team ie as part of the release
notes

More information

http://nbehave.org/

http://www.codeplex.com/NBehave

http://behaviour-driven.org/

http://dannorth.net/

Questions?

You might also like