[Cypress] install, configure, and script Cypress for JavaScript web applications -- part3

Use custom Cypress command for reusable assertions

We’re duplicating quite a few commands between the registration and login of our user for assertions. Let’s see how we can take these assertions and create a custom command to make the assertions.

We have the tests:

    it('should register a new user', () => {
        cy.createUser().then(user => {
            cy.visit('/')
            .getByText(/login/i)
            .click()
            .getByLabelText(/username/i)
            .type(user.username)
            .getByLabelText(/password/i)
            .type(user.password)
            .getByText(/submit/i)
            .click()

            // verify the user in localStorage
            .url()
            .should('eq', `${Cypress.config().baseUrl}/`)
            .window()
            .its('localStorage.token')
            .should('be.a', 'string')
            .getByTestId('username-display', {timeout: 500})
            .should('have.text', user.username)
        })
    });

We can create some assertions commands to make it more reusable:

Cypress.Commands.add('assertHome', () => {
  cy.url().should('eq', `${Cypress.config().baseUrl}/`)
})

Cypress.Commands.add('assertLoggedInAs', user => {
  cy
    .window()
    .its('localStorage.token')
    .should('be.a', 'string')
    .getByTestId('username-display', {timeout: 500})
    .should('have.text', user.username)
})

 

Then we can improve the test:

    it('should register a new user', () => {
        cy.createUser().then(user => {
            cy.visit('/')
            .getByText(/login/i)
            .click()
            .getByLabelText(/username/i)
            .type(user.username)
            .getByLabelText(/password/i)
            .type(user.password)
            .getByText(/submit/i)
            .click()
            .assertHome()
            .assertLoggedInAs(user);
        })
    });

 

Run tests as an authenticated user with Cypress

For most applications you’re going to need to be logged in as a user to interact with the application. Let’s see how we can register as a new user and login as that user to test using the application as a logged in user.

Sometime you want to check some DOM element is not present, you cna use queryByTestId()

    it('displays the username', () => {
        cy.createUser().then(user => {
            cy.visit('/')
                .getByText(/login/i)
                .click()
                .getByLabelText(/username/i)
                .type(user.username)
                .getByLabelText(/password/i)
                .type(user.password)
                .getByText(/submit/i)
                .click()
                .assertLoggedInAs(user)
                .getByText(/logout/i)
                .click()
                .queryByTestId('username-display', {timeout: 300})
                .should('not.exist')
        })
    });

 

Combine custom Cypress commands into a single custom command

 Almost every time we need to login, we’ll want to have a newly created user to login as. Let’s go ahead and combine the createNewUser and logincommands to create a single loginAsNewUser which we can use in any test that needs an authenticated user.

// support/commands.js

Cypress.Commands.add('loginAsNewUser', () => {
    cy.createUser().then(user => {
        cy.login(user)
    });
});

Cypress.Commands.add('login', user => {
    cy.request({
        url: 'http://localhost:3000/login',
        method: 'POST',
        body: user,
    }).then(({body}) => {
        window.localStorage.setItem('token', body.user.token);
        return body.user;
    })
})
// e2e/calcualtor.js

describe('authenticated calculator', () => {
    it('displays the username', () => {
        cy.loginAsNewUser().then((user) => {
            cy.visit('/')
            .getByTestId('username-display')
            .should('have.text', user.username)
            .getByText(/logout/i)
            .click()
            .queryByTestId('username-display', {timeout: 300})
            .should('not.exist')
        })
    });
})

 

Install React DevTools with Cypress

Because Cypress runs in a real Chrome browser, we can install extensions, like React DevTools. The tricky bit will be to make our application hook up to the extension properly.

react-dev-tools.js

if (window.Cypress) {
    window.__REACT_DEVTOOLS_GLOBAL_HOOK__ = window.parent.__REACT_DEVTOOLS_GLOBAL_HOOK__
  }

 

Import the script before we import the REACT

index.js

import './react-dev-tools'

import './global.css'
import React from 'react'

 

posted @ 2018-12-06 21:13  Zhentiw  阅读(431)  评论(0编辑  收藏  举报