bdd: feature this! - yolk recruitment · specflow (.net) lettuce (python) jbehave ... testing...

38
BDD: Feature this!

Upload: hoangthien

Post on 10-Jul-2018

220 views

Category:

Documents


0 download

TRANSCRIPT

Page 1: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

BDD: Feature this!

Page 2: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

Hello!I am Fred HeathYou can find me at

◇ @FredAtBootstrap◇ [email protected]

Page 3: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

What’s this about

❏ Introduction❏ The Whys and Hows❏ Common mistakes and how to avoid them

BDD

Page 4: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

Burning the toast

Page 5: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

The old way

Page 6: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

The BDD way

Features

Step definitions

Code

Page 7: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

BDD Tools

◇ Cucumber (Ruby, Java)◇ CucumberJS (JavaScript)◇ SpecFlow (.NET)◇ Lettuce (Python)◇ JBehave (Java)◇ Behat (PHP)

Page 8: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

Why BDD?

◇ Everyone talks the same language◇ Expectations are fully understood◇ Living documentation◇ Measurable progress◇ Considerable bug reduction

Page 10: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

TDD vs BDD?◇ Dev POV◇ Testing◇ Inside out◇ Assertions◇ Bug reduction as the

objective

◇ Actor POV◇ Specification◇ Outside in◇ Communication◇ Bug reduction as a

side-effect

Page 11: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

“BDD is a communication and collaboration methodology (which happens to facilitate end-to-end testing)

TL;DR

Page 12: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

Rule #1Everyone works together!

Page 13: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

Rule #2Features must be readable by anyone and everyone

Page 14: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

Scenario: View an online meetingGiven I go to domain “http:/myapp.com”, path “/meeting”,

port 80, query parameter ‘meetid=8763652733’When I click on HTML element at XPath

“/local/meeting/view[@class=’btn’]” Then the ‘onclick()’ function (in JS/myscript.js) is triggered for HTML element with id=’meeting1’And the Redis hash with a key ‘meet123’ is set to ‘viewed’And the database trigger tg_upd_meeting is firedAnd the HTML template view_meeting.haml is loaded

Readability: No technical details

Page 15: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

Readability: BackgroundFeature: Change PIN

Background:Given I have been issued a new cardAnd I insert the card, entering the correct PINAnd I choose "Change PIN" from the menu

Scenario: Change PIN successfullyWhen I change the PIN to 1234Then the system should remember my PIN is now 1234

Scenario: Try to change PIN to the same as beforeWhen I try to change the PIN to the original PIN numberThen I should see a warning messageAnd the system should not have changed my PIN

Page 16: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

Readability: OutlinesFeature: Addition

Scenario Outline: Add two numbersGiven the input "<input>"When the calculator is runThen the output should be "<output>"

Examples:| input | output || 2+2 | 4 || 98+1 | 99 |

Page 17: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

Readability: Tags

@slow @reporting @nightlyScenario: Generate data analysis reportGiven I am logged inAnd there is a report "Total widget sales history"…

Timing: @daily, @peak, @nightlyDependencies: @database, @memcache, @proxyProgress: @wip, @todo, @done, @blockedFunctionality: @ux, @analytics, @middlewareEnvironment: @dev, @test, @stage, @live

Page 18: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

Readability: SeguesScenario: Upgrade MembershipWhen I upgrade to the Pro planThen I see a message confirming the upgradeAnd I see that I am now on the Pro planAnd I receive the membership details by emailAnd the database keeps a record of when the upgrade happenedAnd an invoice for the upgrade is generatedAnd a PayPal request is generated

Page 19: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

Readability: SeguesScenario: Upgrade MembershipWhen I upgrade to the Pro planThen the following happens: * I see a message confirming the upgrade * I see that I am now on the Pro plan * I receive the membership details by email * the database keeps a record of when the upgrade happened * an invoice for the upgrade is generated * a PayPal request is generated

Page 20: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

Scenario: User creates some sites and circuits, check connected sites list Given a "site" exists with {"name"=>"Somewhere1", "identifier" => "TER1", "provider"=>"TER1 Provider"} And a "site" exists with {"name"=>"Somewhere2", "identifier" => "TER2", "provider"=>"Some Provider"} And a "site" exists with {"name"=>"Somewhere3", "identifier" => "TER3", "provider"=>"TER3 Provider"} And a "circuit" exists with {"provider_name"=>"Another provider", "redacted_circuit_id"=>"ABC1", "provider_circuit_id"=>"C1", "circuit_type"=>CircuitType.find_by_name("Peering"), "service_type"=>CircuitServiceType.find_by_name("Dark Fiber"), :capacity => CircuitCapacity.find_by_name("1 Gbps"), "physical_wire_type"=>PhysicalWireType.find_by_name("Multi Mode Fiber"), "status"=> CircuitStatus.find_by_name("Cancelled"), "a_end"=>Site.find_by_identifier("TER1"), "b_end"=>Site.find_by_identifier("TER2")} And a "circuit" exists with {"provider_name"=>"Switch and Data", "redacted_circuit_id"=>"ABC2", "provider_circuit_id"=>"C2", "circuit_type"=>CircuitType.find_by_name("Backbone"), "service_type"=>CircuitServiceType.find_by_name("Dark Fiber"), :capacity => CircuitCapacity.find_by_name("1 Gbps"), "physical_wire_type"=>PhysicalWireType.find_by_name("Multi Mode Fiber"), "status"=> CircuitStatus.find_by_name("Cancelled"), "a_end"=>Site.find_by_identifier("TER1"), "b_end"=>Site.find_by_identifier("TER3")} When I am on the "connected_sites" page for site "TER1" Then the "connected-sites-list" should look like | Site ID | Site Name | Site Provider | Provider Circuit ID | Provider Name | Circuit Status | | TER2 | Somewhere2 | Some Provider | C1 | Another provider | Cancelled | | TER3 | Somewhere3 | TER3 Provider | C2 | Switch and Data | Cancelled | I am on the "connected_sites" page for site "TER2" Then the "connected-sites-list" should look like | Site ID | Site Name | Site Provider | Provider Circuit ID | Provider Name | Circuit Status | | TER1 | Somewhere1 | TER1 Provider | C1 | Another provider | Cancelled | When I am on the "connected_sites" page for site "TER3

http://www.elabs.se/blog/15-you-re-cuking-it-wrong

Worst. Scenario. Ever.

Page 21: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

System Actors

Page 22: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

Rule #3Identify and specialise your actors

Page 23: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

Feature Story◇ As a [Specialised Actor]◇ I want [specific System Behavior]◇ So that I can [have a tangible benefit]

Feature: Talks ListingAs a LearnerI want to see abstracts of next meetup’s talksSo that I can see if I like any

Page 24: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

Feature Story◇ As a [Specialised Actor]◇ I want [specific System Behavior]◇ So that I can [have a tangible benefit]

Feature: Talks ListingAs a LearnerI want to see abstracts of next meetup’s talksSo that I can see if I like any decide whether to attend the meetup

------------------------

Page 25: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

Rule #4A feature must tell a valid story

Page 26: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

Scenario: Successful reservation

Given I am on the "Book a place" screenWhen I enter "[email protected]" in "email" fieldAnd I enter "Joe" in "first_name" fieldAnd I enter "Bloggs" in "last_name" fieldAnd I click the "Reserve Now" buttonAnd I enter the displayed captcha in the “captcha” fieldThen a messagebox with green background pops upAnd the message "a place is reserved" appears in the messagebox

Page 27: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

Scenario: Successful reservation

Given I am on the Reservation page

And I enter valid credentials

Then a place is reserved for me

Page 28: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

Rule #5Features are about the ‘what’, not the ‘how’

Page 29: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

Scenario: Session terminated

Given the session has ended

And the user has logged out

Then no more requests will be accepted by the server

???

session: A user session contains information about the user across multiple HTTP requests and is stored in a cookie

Page 30: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

Rule #5Avoid ambiguous terms and speak the Actor’s language

Page 31: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

Case study (original)Feature: Menu item highlighting

Scenario Outline: Menu shows current pageGiven I go to <any_page>Then the side menu should highlight the page I'm currently on

Examples: | any_page | | Home | | About | | Products |

Page 32: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

Case study (modified)Feature: Navigation Link consistency

As the Design DirectorI want to the site to be navigated in the same way as the other company sites So that the company can maintain a consistent corporate image

Scenario Outline: Menu shows current pageGiven I go to <any_page>Then the side menu should highlight the page I'm currently on……

Page 33: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

The colours of success Yellow

Everyone involved in writing features.

Cyan

Readable features.

Red

Behaviour discovery by specialised actors.

Black

Features must tell a valid story.

Purple

Unambiguous vocabulary.

Page 34: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

CreditsSpecial thanks to all the people who made and released these awesome resources for free:

◇ Presentation template by SlidesCarnival◇ Photographs by Unsplash

Page 35: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

Further reading

Page 36: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

Thanks!Any questions?You can find me at:

◇ @FredAtBootstrap◇ [email protected]

Page 37: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

Feature: Accident REST API

As a the visualiser web serviceI can access the accidents resource pageand retrieve relevant accident dataso that I can create accident occurrence visualisations on a map

Scenario: Get all accident dataGiven that there are 6 accident events in the databaseWhen I GET to "http://localhost:1337/accidents"Then I receive a JSON array with 6 objects in the response bodyAnd a status code of 200

Page 38: BDD: Feature this! - Yolk Recruitment · SpecFlow (.NET) Lettuce (Python) JBehave ... Testing Inside out ... Feature: Accident REST API

Given(/^that there are (\d+) accident events in the database$/) do |no_of_accidents| rs = Situation.find(type: "accident") expect(rs.size).to eq(no_of_accidents.to_i)end

When(/^I GET to "([^"]*)"$/) do |page| @page = page res = Net::HTTP.get_response(URI.parse(@page)) @response_code = res.code.to_i @response = JSON.parse(res.body) expect(@response).not_to be nilend