Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Cypress commands (e.g. cy.get) return undefined if previous test step fails #4062

Open
kayonaise opened this issue Apr 29, 2019 · 7 comments

Comments

3 participants
@kayonaise
Copy link

commented Apr 29, 2019

Current behavior:

Cypress test runner fails in after() block with error:

CypressError: cy.first() failed because it requires a DOM element.

The subject received was:

  > undefined

The previous command that ran was:

  > cy.get()

Because this error occurred during a 'after all' hook we are skipping the remaining tests in the current suite:

This happens each time a test step fails. In this case, it happens when the following assertion fails

.get('div.header__dob').should('contain', `${patient.birth_date}`)

Desired behavior:

Cleanup step should execute with Cypress commands returning values instead of undefined

Steps to reproduce: (app code and test code)

  1. Write test with before, test & after steps
  2. Have an assertion fail during testing
  3. cy.get should return undefined in after step

Versions

Cypress: 3.2.0
OS: MacOS 10.14.4
Browser: Electron59 & Chrome73

@jennifer-shehane

This comment has been minimized.

Copy link
Member

commented Apr 30, 2019

Can you provide the portion of your test code that uses the .first() command (including the previous command chained to it) since this is what is printed in the error message?

The error is being thrown when using the .first() command, but it may be displaying in the Command Log at a different point, making this confusing to track down.

@kayonaise

This comment has been minimized.

Copy link
Author

commented Apr 30, 2019

The section of code that fails is

cy.url().should('contain', 'patients')
    .url().should('contain', 'edit')
    .get('h2').first().should('contain', 'Personal information')

The same function is called during an earlier stage in the test and all assertions pass. It is only after the code (pasted in first message) fails that this failure is thrown.

@jennifer-shehane

This comment has been minimized.

Copy link
Member

commented May 2, 2019

This looks related to this issue: #2199 Which we were never able to reproduce.

Does this happen during cypress open, cypress run, both?

Just want to clarify that I understand the structure first and I will try to recreate. The code looks something like this?

context('My tests', () => {
  beforeEach(() => {
    cy.visit('/')
  })

  after(() => {
    cy.url().should('contain', 'patients')
      .url().should('contain', 'edit')
      .get('h2').first().should('contain', 'Personal information')
  })

  it('tests the ui', () => {
    // this test should FAIL
    cy.get('div.header__dob').should('contain', `${patient.birth_date}`)
  })
})
@jennifer-shehane

This comment has been minimized.

Copy link
Member

commented May 2, 2019

I'm able to reproduce with this code below.

describe('subject of undefined thrown in after', () => {
  after(() => {
    cy.get('h2').first()
  })

  it('.make a test fail', () => {
    cy.visit('https://example.cypress.io/commands/actions')
    cy.get('.action-email').should('have.value', 'fake')
  })
})

This error does not throw when the test is in a passing state

CypressError: cy.first() failed because it requires a DOM element.

The subject received was:

  > undefined

The previous command that ran was:

  > cy.get()

Because this error occurred during a 'after all' hook we are skipping the remaining tests in the current suite: 'subject of undefined thrown...'

Screen Shot 2019-05-02 at 12 31 02 PM

Notably, the cy.get('h2') does not exist on the page so should fail with this error instead:

Screen Shot 2019-05-02 at 12 33 28 PM

BUT, in actuality it should have only thrown the error from the failing test, the:

Timed out retrying: expected '<input>' to have value 'fake', but the value was ''
@jennifer-shehane

This comment has been minimized.

Copy link
Member

commented May 2, 2019

I wrote a failing test for this in our code here: #4094

@kayonaise

This comment has been minimized.

Copy link
Author

commented May 2, 2019

Thanks! Glad you were able to reproduce the issue. To answer your previous question, it occurs on both cypress open & cypress run

@superqd

This comment has been minimized.

Copy link

commented May 7, 2019

I have run into this issue as well (I'm a cypress n00b). I worked around it in the after() hook by doing something like this:

after(() => {
   // if a test fails before "after" is called this works
  const $el= Cypress.$("[data-test='lookup-value']");
  cy.wrap($el).click();
         
  // if a test fails before "after" is called, this fails
  //cy.get("[data-test='lookup-value']").click();  
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
You can’t perform that action at this time.