diff --git a/packages/driver/src/cypress/runner.js b/packages/driver/src/cypress/runner.js index fb3abd283f1c..c77a4e8b872b 100644 --- a/packages/driver/src/cypress/runner.js +++ b/packages/driver/src/cypress/runner.js @@ -622,7 +622,7 @@ const _runnerListeners = (_runner, Cypress, _emissions, getTestById, getTest, se // hooks do not have their own id, their // commands need to grouped with the test // and we can only associate them by this id - const test = getTest() || getTestFromHookOrFindTest(hook) + const test = getTestFromHookOrFindTest(hook) if (!test) { // we couldn't find a test to run with this hook diff --git a/packages/runner/cypress/fixtures/hook_spec.js b/packages/runner/cypress/fixtures/hooks/basic_spec.js similarity index 100% rename from packages/runner/cypress/fixtures/hook_spec.js rename to packages/runner/cypress/fixtures/hooks/basic_spec.js diff --git a/packages/runner/cypress/fixtures/hooks/only_spec.js b/packages/runner/cypress/fixtures/hooks/only_spec.js new file mode 100644 index 000000000000..8bf00531c9c9 --- /dev/null +++ b/packages/runner/cypress/fixtures/hooks/only_spec.js @@ -0,0 +1,31 @@ +describe('test wrapper', () => { + it('test 1', () => { + cy.log('testBody 1') + }) + + describe('nested suite 1', () => { + beforeEach(() => { + cy.log('beforeEachHook 1') + }) + + it.only('test 2', () => { + cy.log('testBody 2') + }) + }) + + describe('nested suite 2', () => { + beforeEach(() => { + cy.log('beforeEachHook 2') + }) + + it('test 3', () => { + cy.log('testBody 3') + }) + }) + + describe('nested suite 3', () => { + it.only('test 4', () => { + cy.log('testBody 4') + }) + }) +}) diff --git a/packages/runner/cypress/fixtures/hooks/skip_spec.js b/packages/runner/cypress/fixtures/hooks/skip_spec.js new file mode 100644 index 000000000000..55fac958f4a6 --- /dev/null +++ b/packages/runner/cypress/fixtures/hooks/skip_spec.js @@ -0,0 +1,15 @@ +describe('outer suite', () => { + it.skip('test 1', () => { + cy.log('testBody 1') + }) + + describe('inner suite', () => { + before(() => { + cy.log('beforeHook 1') + }) + + it('test 2', () => { + cy.log('testBody 2') + }) + }) +}) diff --git a/packages/runner/cypress/integration/reporter.hooks.spec.js b/packages/runner/cypress/integration/reporter.hooks.spec.js index b5bf213b7c90..9b58c767b7e1 100644 --- a/packages/runner/cypress/integration/reporter.hooks.spec.js +++ b/packages/runner/cypress/integration/reporter.hooks.spec.js @@ -4,67 +4,119 @@ const { createCypress } = helpers const { runIsolatedCypress } = createCypress() describe('hooks', function () { - beforeEach(function () { - this.editor = {} - - return runIsolatedCypress(`cypress/fixtures/hook_spec.js`, { - onBeforeRun: ({ win }) => { - this.win = win - - win.runnerWs.emit.withArgs('get:user:editor') - .yields({ - preferredOpener: this.editor, - }) - }, + describe('displays hooks', function () { + beforeEach(function () { + return runIsolatedCypress(`cypress/fixtures/hooks/basic_spec.js`) }) - }) - it('displays commands under correct hook', function () { - cy.contains('tests 1').click() + it('displays commands under correct hook', function () { + cy.contains('tests 1').click() - cy.contains('before all').closest('.collapsible').should('contain', 'beforeHook 1') - cy.contains('before each').closest('.collapsible').should('contain', 'beforeEachHook 1') - cy.contains('test body').closest('.collapsible').should('contain', 'testBody 1') - cy.contains('after each').closest('.collapsible').should('contain', 'afterEachHook 1') - }) + cy.contains('before all').closest('.collapsible').should('contain', 'beforeHook 1') + cy.contains('before each').closest('.collapsible').should('contain', 'beforeEachHook 1') + cy.contains('test body').closest('.collapsible').should('contain', 'testBody 1') + cy.contains('after each').closest('.collapsible').should('contain', 'afterEachHook 1') + }) - it('displays hooks without number when only one of type', function () { - cy.contains('tests 1').click() + it('displays hooks without number when only one of type', function () { + cy.contains('tests 1').click() - cy.contains('before all').should('not.contain', '(1)') - cy.contains('before each').should('not.contain', '(1)') - cy.contains('after each').should('not.contain', '(1)') + cy.contains('before all').should('not.contain', '(1)') + cy.contains('before each').should('not.contain', '(1)') + cy.contains('after each').should('not.contain', '(1)') + }) + + it('displays hooks separately with number when more than one of type', function () { + cy.contains('tests 2').click() + + cy.contains('before all (1)').closest('.collapsible').should('contain', 'beforeHook 2') + cy.contains('before all (2)').closest('.collapsible').should('contain', 'beforeHook 3') + cy.contains('before each (1)').closest('.collapsible').should('contain', 'beforeEachHook 1') + cy.contains('before each (2)').closest('.collapsible').should('contain', 'beforeEachHook 2') + cy.contains('test body').closest('.collapsible').should('contain', 'testBody 2') + cy.contains('after each (1)').closest('.collapsible').should('contain', 'afterEachHook 2') + cy.contains('after each (2)').closest('.collapsible').should('contain', 'afterEachHook 1') + cy.contains('after all (1)').closest('.collapsible').should('contain', 'afterHook 2') + cy.contains('after all (2)').closest('.collapsible').should('contain', 'afterHook 1') + }) }) - it('displays hooks separately with number when more than one of type', function () { - cy.contains('tests 2').click() - - cy.contains('before all (1)').closest('.collapsible').should('contain', 'beforeHook 2') - cy.contains('before all (2)').closest('.collapsible').should('contain', 'beforeHook 3') - cy.contains('before each (1)').closest('.collapsible').should('contain', 'beforeEachHook 1') - cy.contains('before each (2)').closest('.collapsible').should('contain', 'beforeEachHook 2') - cy.contains('test body').closest('.collapsible').should('contain', 'testBody 2') - cy.contains('after each (1)').closest('.collapsible').should('contain', 'afterEachHook 2') - cy.contains('after each (2)').closest('.collapsible').should('contain', 'afterEachHook 1') - cy.contains('after all (1)').closest('.collapsible').should('contain', 'afterHook 2') - cy.contains('after all (2)').closest('.collapsible').should('contain', 'afterHook 1') + describe('open in IDE', function () { + beforeEach(function () { + this.editor = {} + + return runIsolatedCypress(`cypress/fixtures/hooks/basic_spec.js`, { + onBeforeRun: ({ win }) => { + this.win = win + + win.runnerWs.emit.withArgs('get:user:editor') + .yields({ + preferredOpener: this.editor, + }) + }, + }) + }) + + it('creates open in IDE button', function () { + cy.contains('tests 1').click() + + cy.get('.hook-open-in-ide').should('have.length', 4) + }) + + it('properly opens file in IDE at hook', function () { + cy.contains('tests 1').click() + + cy.contains('Open in IDE').invoke('show').click().then(function () { + expect(this.win.runnerWs.emit.withArgs('open:file').lastCall.args[1].file).to.include('basic_spec.js') + // chrome sets the column to right before "before(" + // while firefox sets it right after "before(" + expect(this.win.runnerWs.emit.withArgs('open:file').lastCall.args[1].column).to.be.eq(Cypress.browser.family === 'firefox' ? 10 : 3) + expect(this.win.runnerWs.emit.withArgs('open:file').lastCall.args[1].line).to.be.eq(2) + }) + }) }) - it('creates open in IDE button', function () { - cy.contains('tests 1').click() + describe('skipped tests', function () { + beforeEach(function () { + return runIsolatedCypress(`cypress/fixtures/hooks/skip_spec.js`) + }) + + it('does not display commands from skipped tests', function () { + cy.contains('test 1').click() + + cy.contains('test 1').parents('.collapsible').first().should('not.contain', 'testBody 1') + }) + + // https://github.com/cypress-io/cypress/issues/8086 + it('displays before hook when following it.skip', function () { + cy.contains('test 2').click() - cy.get('.hook-open-in-ide').should('have.length', 4) + cy.contains('test 2').parents('.collapsible').first().should('contain', 'before all') + }) }) - it('properly opens file in IDE at hook', function () { - cy.contains('tests 1').click() + describe('only tests', function () { + beforeEach(function () { + return runIsolatedCypress(`cypress/fixtures/hooks/only_spec.js`) + }) + + it('only displays tests with .only', function () { + cy.contains('test wrapper').parents('.collapsible').first().should(($suite) => { + expect($suite).not.to.contain('test 1') + expect($suite).to.contain('nested suite 1') + expect($suite).to.contain('test 2') + expect($suite).not.to.contain('nested suite 2') + expect($suite).not.to.contain('test 3') + expect($suite).to.contain('nested suite 3') + expect($suite).to.contain('test 4') + }) + + cy.contains('test 2').click() - cy.contains('Open in IDE').invoke('show').click().then(function () { - expect(this.win.runnerWs.emit.withArgs('open:file').lastCall.args[1].file).to.include('hook_spec.js') - // chrome sets the column to right before "before(" - // while firefox sets it right after "before(" - expect(this.win.runnerWs.emit.withArgs('open:file').lastCall.args[1].column).to.be.eq(Cypress.browser.family === 'firefox' ? 10 : 3) - expect(this.win.runnerWs.emit.withArgs('open:file').lastCall.args[1].line).to.be.eq(2) + cy.contains('test 2').parents('.collapsible').first().should(($test) => { + expect($test).to.contain('before each') + expect($test).to.contain('test body') + }) }) }) })