** Watch the full recording here: **
Learn how to implement visual testing on your existing test suite, to increase coverage and ensure your UI is bug-free when it's released to the wild.
"You don’t get a second chance to make a first impression!
Join me for this hands-on session, where I will take existing tests and add to them visual testing capabilities that will allow you to test what your app looks like, and not only how it behaves. I promise: all this goodness - in just 8 lines of code!"
- Gil Tayar, Sr. Software Architect @ Applitools
======
Automated tests are great at testing *functionality*, but do they check how your app appears to the end user? Do they check that the "submit" button is aligned with the edit box? Do they check that the background color is that perfect shade of pale? NOPE!
What if we told you that in 8 lines of code, you can add vision to your existing tests, and check how your app appears to your users, and not just how it behaves.
Moreover, once you add vision to your existing tests, you can supercharge your functional checks and check the whole page in one big assertion.
Watch this step-by-step and very hands-on session, and learn:
-- What visual testing is and how it can augment your existing regression automation test suite
-- How you can enhance your existing functional tests with visual testing
-- How easy it is to write code that visually tests an entire application
Visual Testing: Turbo-Charge Your Functional Tests with Visual Powers in Just 8 Lines of Code -- by Gil Tayar
1. @giltayar
You’re almost there:
turbocharge your functional tests
with visual powers
Gil Tayar (@giltayar)
August 2018
This presentation: http://bit.ly/turbocharge-webinar
Github repo: https://github.com/giltayar/realworld-frontend-testing
2. @giltayar@giltayar
About Me ● My developer experience goes all the way
back to the ‘80s.
● Am, was, and always will be a developer
● Testing the code I write is my passion
● Currently evangelist and architect @
Applitools
● We deliver Visual Testing tools:
If you’re serious about testing, checkout
Applitools Eyes
● Sometimes my arms bend back
● But the gum I like is coming back in style
@giltayar
11. @giltayar
● Huge library (npm)
○ Biggest.
○ Very high quality
○ Lots of tests!
● DLL hell is gone (almost…)
● No bullshit libraries (readme-s,
not javadocs)
I love NodeJS
● Constantly improving in
performance
● Fast startup times
● ES2018 is a wonderful language
● Async programming is
wonderful
● Good FP language too
● Constantly evolving
12. @giltayar
● All the cool new automation frameworks are in
NodeJS/JavaScript
● It is the language of the frontend developers
○ Writing tests with the frontend developers
○ Code sharing!
I love NodeJS
26. @giltayar
// action: click on new post
const newPost = await driver.findElement (By.partialLinkText ('New Post'))
await newPost.click()
await waitFor('input[placeholder="Article Title"]' )
// action: set the title, description, and article
await setText('input[placeholder="Article Title"]' , 'a title')
await setText('input[placeholder="What's this article about?"]' , 'something' )
await setText('textarea[placeholder*="Write your article"]' , 'wonderful' )
// action: set the tags
const tags = await driver.findElement (By.css('input[placeholder="Enter tags"]' ))
for (const tag of ['a', 'b', 'c']) await tags.sendKeys(tag, Key.ENTER)
// action: submit form
await click('button[type=button]' )
Publish a Post
27. @giltayar
See that it’s there, and add a comment
validation
validation
validation
validation
action
action
37. @giltayar
Problems with Validations
● Fragile Selectors
● Complex Code
● Too much to validate
● Only positive check
○ We don’t validate what we don’t know about
● Solution: Page Objects, partially
39. @giltayar
Let’s see why validations are holistic
● Add the following to Register.js:
onSubmit: (username, email, password) => {
dispatch({ type: UPDATE_FIELD_AUTH, key: 'username', value: '' })
const payload = agent.Auth.register(username, email, password);
● This will clear the username after every submit
51. @giltayar
Solutions to problems with validations
● Fragile Selectors
○ No more selectors
● Complex Code
○ Same code for all validations
● Too much to validate
○ We validate holistically
● Only positive check
○ We validate things we didn’t even think of validating
52. @giltayar
Solutions to problems with validations
● Fragile Selectors
○ No more selectors
● Complex Code
○ Same code for all validations
● Too much to validate
○ We validate holistically
● Only positive check
○ We validate things we didn’t even think of validating
53. @giltayar
Let’s try it out...
● Run the tests without the bug
● Copy baseline image to expected-screenshots folder
● Add the following to Register.js:
onSubmit: (username, email, password) => {
dispatch({ type: UPDATE_FIELD_AUTH, key: 'username', value: '' })
const payload = agent.Auth.register(username, email, password);
● This will clear the username after every submit
54. @giltayar
Functional vs Visual Validations
● Let’s test it in step2: functional validations
git checkout step2 && npm run build && npm test
● The test passes! (and it shouldn’t)
● Now let’s try step3: visual validations
git checkout step2 && npm test
● The test fails! (as it should)
59. @giltayar
// goto home page
await driver.get('http://localhost:3000/')
// validate post author
expect(await getText('a.author'))
.to.equal('ausername')
// validate post title
expect(await getText('.article-preview h1'))
.to.equal('a title')
// validate post description
expect(await getText('.article-preview h1 + p'))
.to.equal('something')
// validate post tags
expect(await getText('.article-preview ul'))
.to.equal('abc')
And this long code...
// validate popular tags
expect(await getText('.sidebar .tag-list'))
.to.equal('abc')
// action: goto post page
await click('.article-preview h1')
await waitFor('.article-page')
// validate post title
expect(await getText('h1')).to.equal('a title')
// validate article description
expect(await getText('div.article-content p'))
.to.equal('wonderful')
// validate article tags
expect(await getText('ul.tag-list')).to.equal('abc')
60. @giltayar
async function validateBlog() {
await driver.get('http://localhost:3000/')
await checkWindow('anonymous-home-page')
await click('.article-preview h1')
await waitFor('.article-page')
await checkWindow('anonymous-blog-post-view')
}
Into this...
61. @giltayar
Solutions to problems with validations
● Fragile Selectors
○ No more selectors
● Complex Code
○ Same code for all validations
● Too much to validate
○ We validate holistically
● Only positive check
○ We validate things we didn’t even think of validating
62. @giltayar
Problems with Naive Image Diffing
● Small anti-aliasing differences
○ Mac vs. Linux vs. Windows
○ Different GPUs
● Date/time problems
○ regions that are different from run to run
● Full screen vs. Viewport
● Comparing is a pain
● “Accepting” a new baseline is a pain
63. @giltayar
Problems with Naive Image Diffing
● Small anti-aliasing differences
○ Mac vs. Linux vs. Windows
○ Different GPUs
● Date/time problems
○ regions that are different from run to run
● Full screen vs. Viewport
● Comparing is a pain
● “Accepting” a new baseline is a pain
65. @giltayar
Cloud-based solution
● Visual diffing algorithms see like a human sees
○ Ignoring the small differences
○ AI-level algorithms are now involved and keep getting better
● Screenshot management tools are available, enabling you to
○ See the diffs
○ Approve new baselines
○ Open bugs on diffs that are bugs
66. @giltayar
Let’s Run the Demo
https://github.com/giltayar/realworld-frontend-testing, branch step4
69. @giltayar
Supercharging Your Test with Visual Validations
● Write code that issues action after action, to create a long story
○ You can use a recorder like Selenium IDE or one of the new cloud-based
ones
● Intersperse your code with visual validations
○ You can use the open-source solutions or a cloud-based option
● You get two for the price of one:
○ Much simpler functional validations
○ Visual validation of your page: catch those visual bugs that you couldn’t
catch till now!
70. @giltayar
Thank You
Gil Tayar (@giltayar)
This presentation: http://bit.ly/turbocharge-webinar
The Github repo: https://github.com/giltayar/realworld-frontend-testing