2

From response A (/list.json) my app receives a list of items. Based on the output of A, my app makes another set of requests B for individual items (/one.txt, /two.txt, ...).

Now in my test I want to make sure that all responses B return HTTP 200.

Waiting (cy.wait) for response A is fine. However, waiting for responses B is more difficult, because I have to start waiting just upon receiving response A where I learn about responses B.

I tried 2 options:

  1. start waiting inside of cy.wait of response A - code,
  2. start waiting outside of cy.wait of response A - code

Neither of those work. With option 1 I get

`cy.wait()` timed out waiting `5000ms` for the 1st request to the route: `one.txt`. No request ever occurred

And with option 2 I get a pass, even though /two.txt doesn't exist. Looks like cy.wait for responses B is added after the responses were received

Fody
  • 23,754
  • 3
  • 20
  • 37
gicig
  • 334
  • 3
  • 14

1 Answers1

2

Since all requests are triggered off the visit, and are dynamic, you need a single intercept that handles all requests.

To me that means adding some javascript and dynamic aliases.


// avoid status code 304, disable browser cache
Cypress.automation('remote:debugger:protocol', {
  command: 'Network.clearBrowserCache'
})


describe('spec', () => {
  it('test', () => {
    let items = [];
    cy.intercept('GET', '*', (req) => {

      const slug = req.url.substring(req.url.lastIndexOf('/') + 1)
      if (slug === 'list.json') {
        req.alias = 'list'
      } 
      if (items.includes(slug)) {
        req.alias = 'item'
      }

      req.continue((res) => {
        if (slug === 'list.json')) {
          items = res.body;
        }  
      })
    })

    cy.visit('https://demo-cypress.netlify.app');  

    cy.wait('@list')                          // wait for list
      .then(() => {                           // now items is populated
        for (let item of items) {             // really just need the count
          cy.wait('@item').then(interception => {     // wait n-times
            expect(interception.response.statusCode).to.eq(200);
          })
        }
      })
  })
})
Fody
  • 23,754
  • 3
  • 20
  • 37
  • I set up the sample page to showcase the issue, but in the real app there's more to it. E.g., individual items' responses are cached in localStorage and on subsequent requests localStorage is checked. If localStorage contains items the app doesn't request them. I will update the sample page to reflect that – gicig Sep 02 '22 at 09:54
  • Yes I can see the calls in the network tab. I have a better approach. – Fody Sep 02 '22 at 09:59
  • Modified to assign `alias` on the request call and `items` on the response. It catches the first and second items, but status code for 2nd is `304`. – Fody Sep 02 '22 at 10:20
  • Modified to avoid `main.js` and any other app loading artifacts. – Fody Sep 02 '22 at 10:34
  • A clever way to do it. Thank you very much – gicig Sep 02 '22 at 11:24