Disrupting WEb Application TESTING

with Cypress.io

slides.com/brandonb927/testing-web-applications-with-cypress

Hi, I'm

Brandon Brown

QA Developer @ Dyspatch

@brandonb927

brandonb.ca

QA for Dyspatch

A cloud-based communications management platform that helps Enterprise organizations centralize their email creation, approval, and publishing processes.

Startup Slam

startupslam.io

Battlesnake

battlesnake.io

Dyspatch Events

TestING CODE

Why test your code?

It's fun!

It will save you time

It's good practice

Reduces side effects

Mitigate regressions

Codebases are built on unit tests, supplemented by integration tests, topped with end-to-end tests.

 

Unit tests are supposedly where you spend your time in testing code. Integration tests are where you spend slightly less time.

 

Cap it off with a small set of "happy path" end-to-end tests.

 

The Original Test PYramid

Mike Cohn, circa 2004

Times Have Changed Though

"The Testing Trophy" 🏆

 

A general guide for the **return on investment** 🤑 of the different forms of testing with regards to testing JavaScript applications.

 

- End to end w/ @Cypress_io ⚫️
- Integration & Unit w/ @fbjest 🃏
- Static w/ @flowtype 𝙁 and @geteslint ⬣

Kent C. Dodds

@kentcdodds
PayPal Eng & TC39 Member

The Testing Trophy

 

  • Static checks: Flow, ESLint → first line of defense on catching problems in our code
  • Integration tests give the biggest bang for our buck, and should be prioritized accordingly.
  • Unit tests can fill in the gaps, and E2E tests can confirm the happy paths of your app remain fully functional.

Bottom ⇒ Up

  • Cheap ⇒ Expensive
  • Simple problems like linting get solved here ⇒ Big problems like "login or checkout flow" are solved here
  • Static checks are fast ⇒ E2E tests are slow

Great advice,

what does it mean?

2 Unit Tests. 0 Integration Tests.

Writing Lots Of Unit tests is easy because We have tools that make it easy

$ npm install -d jest
$ npm test
const foo = require('./foo')
describe('foo', () => {
  it('adds bar', () => {
    expect(foo('bar')).toBe('foobar')
  })
})

1. Install unit-testing framework

3. Run the tests

2. Write a unit test

2 Unit Tests. 0 Integration Tests.

End to End Testing

What is it?

"End to end" (shortened to E2E) is methodology used to test whether the flow of an application is performing as designed from start to finish. E2E ensures the happy path is maintained for customers.


Unit tests and integration tests only take a small piece of the application and assess that piece in isolation.

 

Even if these pieces work well by themselves, you don’t necessarily know if they’ll work together as a whole. Having a suite of end-to-end tests on top of unit and integration tests allows us to test our entire application.

  • E2E tests are very slooow 🐢 (compared to unit tests)
  • Finding the root cause of E2E test failures can be difficult, especially in CI land with no GUI
  • Flaky tests are easy to write, best to understand whether what you're testing is important in the first place
  • Async workflow makes sync code and conditional testing difficult ⇒ Write more guards

 

Caveats

Selenium + WebDriver

OG Browser Automation Tool

  • one of the best automated browser tools for testing applications
  • open source, contributed to by ~35 people
  • runs outside the browser and executes remote commands across the network into the browser
  • can be bundled with any software for testing so long as there is language bindings
  • can be used with many programming languages

Selenium

Pictured: An operator running the Selenium test suite for their app

Cypress Overview

  • Built for web developers by web developers

  • Automated testing INSIDE a browser

  • Incredible developer experience

  • Amazing & well-written docs

  • Easily write "happy path" tests for  workflows that could go untested/unnoticed in production

  • Focuses on doing E2E testing REALLY well

  • Works on any front-end framework or website

  • 🚫 No Selenium ⇒ ✅ Electron, Chromium (more browsers eventually)

Cypress Overview

  • Tests are written in JavaScript, run in isolation (via js function closures)

  • Utilizes Mocha, Chai, and Sinon under the hood for BDD syntax, test assertions, and function stubs/spies

  • Cookies, session, application state, etc. is encapsulated in a browser window
  • Tests have access to native web APIs and everything in your application code as well
  • Debugging tests is a breeze

    • DevTools access in the test runner UI, like a browser

    • Readable text output and optional JUnit test reports in CI/headless mode

  • Docker images for CI/headless mode

Cypress Overview

Cypress is most often compared to Selenium; however Cypress is both fundamentally and architecturally different. Cypress is not constrained by the same restrictions as Selenium.

This enables you to write faster, easier and more reliable tests.

Selenium

Cypress

Installing Cypress

$ npm install -d cypress
 λ npm install -d cypress

> cypress@2.1.0 postinstall /Users/brandon/p/node_modules/cypress
> node index.js --exec install

Installing Cypress (version: 2.1.0)

 ✔  Downloaded Cypress
 ✔  Unzipped Cypress
 ✔  Finished Installation /Users/brandon/p/node_modules/cypress/dist/Cypress.app

You can now open Cypress by running: node_modules/.bin/cypress open

https://on.cypress.io/installing-cypress

Installs cypress into your current project/folder

Using Cypress

$ ./node_modules/.bin/cypress open

Opens the Cypress test runner UI

Using Cypress

Writing a TeST

describe('My First Test', () => {
  it('Gets, types, and asserts', () => {
    cy.visit('https://example.cypress.io')

    cy.contains('type').click()

    // Should be on a new URL which includes '/commands/actions'
    cy.url().should('include', '/commands/actions')

    // Get an input, type into it, and verify that the value has been updated
    cy.get('.action-email')
      .type('fake@email.com')
      .should('have.value', 'fake@email.com')
  })
})
$ touch cypress/integration/home_page_spec.js

Testing the flow of navigation & form input value

Creates the empty spec file

Running a TeST

It's That Easy with Cypress!

Demo Time?

Resources

Thanks For Listening!

@brandonb927

brandonb.ca

slides.com/brandonb927/testing-web-applications-with-cypress

Disrupting Web Applications Testing with Cypress

By Brandon Brown

Disrupting Web Applications Testing with Cypress

In this talk, I'm going to go over a few different test methods for code that we as developers use today, and show you that certain test paradigms haven't held up well with time. I will also give you a fairly involved take on some new software you can use today to test all aspects of your web application!

  • 1,012