Reputation: 157981
I have the following test for a custom Cypress command of mine:
it('can navigate to a url', () => {
const history = createHistory();
cy.window().then(win => ((win as any).__chh__history__ = history));
cy.spy(history, 'push');
history.listen((location, action) => {
expect(action).to.equal('PUSH');
expect(location.pathname).to.equal(PATH);
expect(location.state).to.equal('foobar');
});
cy.navigate(PATH, 'foobar');
cy.wait(0).then(() => {
expect(history.push).to.have.been.called;
});
});
The command works fine, but if I remove the cy.wait(0)
, only doing the expect
, then the test fails.
I assume it's because the cy.navigate
command (added via Cypress.Commands.add
) is queued, like other Cypress commands, meaning the expect
actually runs before any of the Cypress commands have even started?
If so, that's fine and as expected of course, but is there a way in Cypress tests to queue things, without using cy.wait(0)
?
For example when I'm checking elements, I can use cy.get(something).should($el => expect(...))
, but in this case, there's nothing to "should on"... I could of course cy.get('body')
or whatever, but I don't really want to get anything in this case. 🤔
Upvotes: 1
Views: 1008
Reputation: 23463
The docs show use of a naked expect()
after the spy has been established,
cy.spy(util, 'addListeners')
App.start()
expect(util.addListeners).to.be.called
but I think this is misleading, since expect()
runs immediately but intervening Cypress commands may have inherent delays or reties, and can't be guaranteed to complete before the expect is executed.
Two other ways to test this are:
Ensure the expect is only run after your custom command
cy.navigate(PATH, 'foobar').then(() => {
expect(history.push).to.have.been.called;
})
Put the expectation into the Cypress command queue
cy.navigate(PATH, 'foobar');
cy.wrap(history).its('push').should('have.been.called')
Upvotes: 1