cypress: Misleading error message when trying to access (probably) detached DOM-Element

Some of our tests sometimes showed the following error message: cy.contains() failed because it requires the subject be a global window object.

This wasn’t very helpful at all, because the check looked something like this: cy.get("foo").contains("bar")

The cy.get("foo") obviously is not a window-object.

After digging around in the source code, I think the following line is the problem: https://github.com/cypress-io/cypress/blob/052892d79f95f9792e00d426722a9d904b572df4/packages/driver/src/cy/ensures.js#L84

When all tests fail on the type, only the first error is shown, which in the “contain”-Case is the check if it is a window-object. It probably should show all errors, as then a user would also see the “cy.get(“foo”) is detached”-error. This would help in trying to debug applications which seem to fail at random.

About this issue

  • Original URL
  • State: closed
  • Created 4 years ago
  • Reactions: 11
  • Comments: 16 (6 by maintainers)

Most upvoted comments

Have the same problem

@jayarjo The “real” case was a bit more complicated, where we replaced one part of the page dynamically with a response from the server. So maybe you have the same problem, where you initialize the page, do something asynchronously and replace some DOM-elements with new ones? Then, if you hold onto a reference of the old (now detached) element you get the error, while in the browser it looks like everything is still there.

This is still a problem.

@pakaufmann have you detected what was causing it? In my case it is not clear, 'cause DOM element is clearly on the page.

This is the simplest example I could come up with:

Test:

describe('This test', () => {
  it('will fail with a confusing error message', () => {
    cy.visit('/page-1.html');
    const willFail = cy.get('#failing').click().contains('not attached');
  })
})

page-1.html:

<html>
<head>
</head>
<h1>Page 1</h1>
<div id="failing">not attached</div>
<script>
const el = document.getElementById('failing');

el.addEventListener('click', function(e) {
    el.remove();
});
</script>

</html>

The error message the test will output is CypressError: cy.contains() failed because it requires the subject be a global window object., instead of something like cy.contains() failed because the element was not attached to the DOM.