45
Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow BDDx, London 11 th November 2016 Gáspár Nagy coach trainer bdd addict creator of specflow @gasparnagy [email protected]

Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Embed Size (px)

Citation preview

Page 1: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Behavior Driven Web UI Automationwith Selenium and Cucumber/SpecFlowBDDx, London11th November 2016

Gáspár Nagycoach • trainer • bdd addict • creator of specflow

@gasparnagy • [email protected]

Page 2: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

bddaddict.com

bdd addict

given.when.then

CAUTION!

on the stage

Page 3: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

There are problems with UI testing!

scriptexpressed

using UI terms

modeling gapbetween UI terms and

domain model terms

sloooowfor a bigger app the

feedback loop gets

uselessly long

brittlebrowsers changing,

environment

changes, cross-

platform issues, etc.

Page 4: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

You are here*!*hopefully

Page 5: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

A decent app

Page 6: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

With an ugly test…

Page 7: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)
Page 8: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

Unclear

purposeCode

duplication

Anti-

semantic

locators

Wrong

abstraction

Timing

issues

Page 9: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

Unclear purpose – BDD

• Automated tests are investments for the future

• Tests without clearly specified goal are only good until they pass

• BDD/SpecFlow/Cucumber are great tools for helping you to connect purpose for the automation steps

• Scenario title – defines the goal (“The one where …”)

• Scenario steps – provide a functional grouping for the automation steps

Page 10: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

Introduce SpecFlow/Cucumber

Page 11: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

Introduce SpecFlow/Cucumber

Page 12: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

Code duplication – Page Objects

• A small change in the application should only make a small impact on the automation solution

• Automated tests should support you for applying changes and not hold you back

• Page Objects can help you to encapsulate the automation logic for particular UI elements

• Page Objects mirror the page structure

• They represent an automation layer below the step definitions

• Driver pattern is a generalization of the page object pattern for non-UI automation tasks

• They can serve as the interface for switching from UI automation to API-level automation

Page 13: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

Introduce Page Objects

Page 14: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

Introduce Page Objects

Page 15: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

Introduce Page Objects

Page 16: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

Page 17: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

Anti-semantic locators

• Think about how your users identify the different information (text, data, controls, buttons, etc.) on the page

• If the user can find them, you will also find them… be smart!

Page 18: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

Locators – Match your solution to the domain

• If the solution is modeled on the basis of the problem space, the elements will have semantic identification

• Question title – title column in DB – Title property in code - #Title

[FindsBy(How = How.Id)] public IWebElement Title { get; set; }

Page 19: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

Problem vs. solution domain

Concept by Matt Wynne, see also http://dannorth.net/2011/01/31/whose-domain-is-it-anyway/

Problem Domain Solution Domain

Tweet• Tweet

• Retweet

Message• Send

• Forward

Page 20: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

Locating by ID is not enough!

[FindsBy(How = How.Id, Using = "fabric_input")]public IWebElement Fabric { get; set; }

fabric

fabric_input

fabric_list

fabric_open

@Html.Kendo().ComboBox().Name("fabric")

These are

internal for

the control!

Page 21: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

Locating by ID is not enough!

[FindsBy(How = How.Id, Using = "cb9eb8be-71…")]public IWebElement Khaki { get; set; }

Page 22: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

Be careful with Selenium IDE

[FindsBy(How = How.CssSelector, Using = "input.btn.btn-default")]public IWebElement Fabric { get; set; }

There was only one button on the page that time!

Page 23: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

Define your own location strategy and implement it as a custom locator!

[FindsBy(How = How.Custom, CustomFinderType = typeof(TableFieldLocator)]

public IWebElement UserName { get; set; }

form

This is a

generic

lookup

strategy

User Name

Password

input

input

Page 24: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

public IWebElement UserName { get; set; }

Apply conventions with decorators and find the tester’s nirvana…

form

This is the

app-specific

lookup

strategy

User Name

Password

input

input

Page 25: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)
Page 26: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

Unclear

purposeCode

duplication

Anti-

semantic

locators

Wrong

abstraction

Timing

issues

Page 27: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

Wrong abstraction

Page 28: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

Concept is an idea or mental picture of a group or class of objects formed by combining all their

aspects

Page 29: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

This

gonna

save it!

Page 30: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

UI Concepts

Counter concept,

divs and spans

Short-text entering

concept, input

@type=text

Multi-line text

entering concept,

div+javascriptSingle-choice

concept,

set of input

@type=radioSubmit concept,

span+javascript

Page 31: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

Encapsulate automation logic of UI concepts

• Selenium’s PageFactory can only map IWebElement or List<IWebElement>

• Defining a static helper method is already a good solution• like FillInTextBox(IWebElement elm, string value)

• A factory infrastructure, similar to the PageFactory makes it even better

Page 32: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

A concept-based page

express concepts

interact on concept

level

Page 33: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

Thread.Sleep(3000);

Page 34: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

Why do we have this timing problem?

Page 35: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

An example

Enter text

Post form

Working, working…

Observe result

title.SendKeys(…);

button.Click();

driver.FindElement(…);

Page 36: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

Let’s add some waiting to it!

Thread.Sleep(2000);

var wait = new WebDriverWait(driver, TimeSpan.FromSeconds(5));wait.Until(d => d.FindElement(By...));

driver.Manage().Timeouts().ImplicitlyWait(TimeSpan.FromSeconds(5));...driver.FindElement(By...);

Static waiting

Busy/active waiting

Implicit busy waiting

Page 37: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

An example

Enter text

Post form

Working, working…

Observe result

title.SendKeys(…);

button.Click();

driver.FindElement(…);

The thing you are waiting for is here!

You are waiting here!

Page 38: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

Waiting at the observation step…

• Establishes an implicit dependency between the automation code triggering the action (Click) and the assertion (FindElement)

• This makes the code brittle, because• you cannot compose new tests easily from the automation steps (e.g. the same

assertion after another action)

• the code will be sensitive to the order of the assertions

• tests will be slowed down unnecessarily

Page 39: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Your user knows* when the action is done*hopefully

• Maybe there is a progress indicator

• Maybe they look at the browser icon

• Maybe they’ll wait till they see the end of the page

Page 40: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

An example

Enter text

Post form

Working, working…

Observe result

title.SendKeys(…);

button.SubmitClick();

driver.FindElement(…);

Result page loaded

Page 41: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

Define the waiting conditions for the interactions of the UI concepts!

This is an example…

• Submit concept – a concept that can trigger a server-side processing and results either in an error or a success

• Success is indicated by a fully loaded page with a success message

• Error is indicated by …

• Fully loaded page means that the footer is visible

• Solution: Implement SubmitConcept.Click() in a way that it clicks the button and is waiting either for the success or the error condition

Page 42: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Copyright © Gaspar NagyCopyright © Gaspar Nagy

Other conditions

• Wait until progress indicator is unloaded

• Wait until injected JavaScript signals that the operation has finished

• Wait until protractor signals

• You can even put Thread.Sleep there… only to that single place!

For all these, you need to isolate Submit/Click from other clicks

Page 43: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)
Page 44: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

*maybe

Page 45: Behavior Driven Web UI Automation with Selenium and Cucumber/SpecFlow (BDDx London, 11/11/2016)

Gáspár Nagycoach • trainer • bdd addict • creator of specflow

@gasparnagy • [email protected]

Gáspár Nagycoach • trainer • bdd addict • creator of specflow

@gasparnagy • [email protected]

Thank you!