Ways of fixing flaky tests in Cypress
Problem Statement
The flakiness of the test cases is one of the biggest challenges in any automation tool. There are different ways of fixing flaky tests in cypress.
Almost 16% of our tests have some level of flakiness associated with them! This is a staggering number; it means that more than 1 in 7 of the tests written by our world-class engineers occasionally fail in a way not caused by changes to the code or tests.
Different ways of fixing flaky tests in Cypress
- Adding
.contains('element')
.should('be.visible')
,.should('exist')
before clicking on the element - Test Retires
- Use timeouts instead of waits
- Use cy.intercept() to wait for the XHR request to finish execution.
1. Adding.Exist,.visible before Clicking on the element
The first and very straightway to reduce the flakiness is to use .should('exist')
.should('be.visible')
.contains('element')
2. Test Retires
Cypress.io team introduces “test retries” in version 5.0.0 which helps us to save time for running the failed test cases.
Configure Test Retries
- Global configuration
- Custom configuration
1. Global configuration: We can configure this in the configuration file cypress.json bypassing the retries option for an object with the following options:
runMode
allows you to define the number of test retries when runningcypress run
openMode
allows you to define the number of test retries when runningcypress open
In the above case, the cypress will retry 2 times if required data is not found and the test case Is failed.
If the test case passed in 1st-time cypress moves to other test cases. if the test case is failed will try 1st retry Attempt
If 1st retry attempt failed will try 2nd retry option.
If 2nd retry attempt failed Cypress will mark the test as failed and then move on to run any remaining tests.
So total 3 attempts (*One when test case run the first time and the other 2 attempts for retry )
2. Custom configuration:
In Custom configuration we can configure in Individual Test Level and Test Suite Level.
Individual Test Level (*In the It block)
Test Suite Level (In describe block)
3. Use timeouts instead of waits
Sometimes we need a higher timeout for the particular element to load. We can give timeout inside cy. get() in the following way.
cy.get(“#first-name”, {timeout: 10000}).type(“Mike”)
4. Use cy. intercept() to wait for the XHR request to finish execution.
We can usecy.intercept()
to wait for the XHR request to finish execution. We can intercept the particular network call and wait till the call is not finished.
Example : cy.intercept(‘http://xyz.com/model').as('getModel') //Intercept the url
Use cy.wait() with aliasing an intercepted route to wait for the request/response cycle to complete.
In the below screenshot after clicking on the form model, we presume there is some unfinished request. cy.wait() wait for the request/response cycle to complete. By using the cy.wait("@getModel")
we have access to the XHR
object.
So till the request is not complete Cypress will wait for the API call to finish before continuing. So in this way, we can save test cases from failure.
Conclusion
I would suggest using intercept the network call when there are flaky test cases and far-off from cy.wait(milliseconds).
Channel
https://www.youtube.com/channel/UCrRPMnWk2slXl4xFOVXfTmQ?sub_confirmation=1