Skip to content

Add retry-ability to the cypress adapters for dom-testing-library #78

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

Merged
merged 7 commits into from
Sep 4, 2019
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
59 changes: 44 additions & 15 deletions cypress/fixtures/test-app/index.html
Original file line number Diff line number Diff line change
Expand Up @@ -23,47 +23,76 @@
click <span title="Run All Tests">↻</span> Run All Tests.
</blockquote>
<section>
<h2>getByPlaceholderText</h2>
<input type="text" placeholder="Placeholder Text" />
<h2>*ByLabel and *ByPlaceholder</h2>
<label for="by-text-input">Label 1</label>
<input type="text" placeholder="Input 1" id="by-text-input" />

<label for="by-text-input-2">Label 2</label>
<input type="text" placeholder="Input 2" id="by-text-input-2" />
</section>
<section>
<h2>getByText</h2>
<button onclick="this.innerText = 'Button Clicked'">Button Text</button>
<h2>*ByText</h2>
<button onclick="this.innerText = 'Button Clicked'">Button Text 1</button>
<div id="nested">
<h3>getByText within</h3>
<button onclick="this.innerText = 'Button Clicked'">Button Text</button>
<h3>ByText within</h3>
<button onclick="this.innerText = 'Button Clicked'">Button Text 2</button>
</div>
</section>
<section>
<h2>getByLabelText</h2>
<label for="input-labelled-by-id">Label For Input Labelled By Id</label>
<input type="text" placeholder="Input Labelled By Id" id="input-labelled-by-id" />
<h2>*ByDisplayValue</h2>
<input type="text" value="Display Value 1" />

<input type="text" value="Display Value 2" />
</section>
<section>
<h2>getByAltText</h2>
<h2>*ByAltText</h2>
<img
src="data:image/png;base64,"
alt="Image Alt Text"
alt="Image Alt Text 1"
onclick="this.style.border = '5px solid red'"
/>
<img
src="data:image/png;base64,"
alt="Image Alt Text 2"
onclick="this.style.border = '5px solid red'"
/>
</section>
<section>
<h2>*ByTitle</h2>
<span title="Title 1">1</span>
<span title="Title 2">2</span>
</section>
<section>
<h2>*ByRole</h2>
<div role="dialog">dialog 1</div>
<div role="dialog-fake">dialog 2</div>
</section>
<section>
<h2>getByTestId</h2>
<h2>*ByTestId</h2>
<img
data-testid="image-with-random-alt-tag"
data-testid="image-with-random-alt-tag-1"
src="data:image/png;base64,"
onclick="this.style.border = '5px solid red'"
/>
<img
data-testid="image-with-random-alt-tag-2"
src="data:image/png;base64,"
onclick="this.style.border = '5px solid red'"
/>
</section>
<section>
<h2>getAllByText</h2>
<h2>*AllByText</h2>
<button onclick="this.innerText = 'Jackie Kicked'">Jackie Chan 1</button>
<button onclick="this.innerText = 'Jackie Kicked'">Jackie Chan 2</button>
</section>
<section>
<h2>*ByText on another page</h2>
<a onclick='setTimeout(function() { window.location = "/next-page.html"; }, 100);'>Next Page</a>
</section>
<!-- Prettier unindents the script tag below -->
<script>
document
.querySelector('[data-testid="image-with-random-alt-tag"]')
.querySelector('[data-testid="image-with-random-alt-tag-1"]')
.setAttribute('alt', 'Image Random Alt Text ' + Math.random())
</script>
</body>
Expand Down
29 changes: 29 additions & 0 deletions cypress/fixtures/test-app/next-page.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<title>cypress-testing-library</title>
<style>
blockquote {
margin: 0;
border-left: 4px solid grey;
padding-left: 10px;
color: grey;
}
section {
padding: 10px;
}
</style>
</head>
<body>
<blockquote>
No auto-reload after changing this static HTML markup:
click <span title="Run All Tests">↻</span> Run All Tests.
</blockquote>
<section>
<h2>New Page Loaded</h2>
</section>
</body>
</html>
69 changes: 0 additions & 69 deletions cypress/integration/commands.spec.js

This file was deleted.

130 changes: 130 additions & 0 deletions cypress/integration/find.spec.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,130 @@
describe('find* dom-testing-library commands', () => {
beforeEach(() => {
cy.visit('/')
})

// Test each of the types of queries: LabelText, PlaceholderText, Text, DisplayValue, AltText, Title, Role, TestId

it('findByLabelText', () => {
cy.findByLabelText('Label 1')
.click()
.type('Hello Input Labelled By Id')
})

it('findAllByLabelText', () => {
cy.findAllByLabelText(/^Label \d$/).should('have.length', 2)
})

it('findByPlaceholderText', () => {
cy.findByPlaceholderText('Input 1')
.click()
.type('Hello Placeholder')
})

it('findAllByPlaceholderText', () => {
cy.findAllByPlaceholderText(/^Input \d$/).should('have.length', 2)
})

it('findByText', () => {
cy.findByText('Button Text 1')
.click()
.should('contain', 'Button Clicked')
})

it('findAllByText', () => {
cy.findAllByText(/^Button Text \d$/)
.should('have.length', 2)
.click({ multiple: true })
.should('contain', 'Button Clicked')
})

it('findByDisplayValue', () => {
cy.findByDisplayValue('Display Value 1')
.click()
.clear()
.type('Some new text')
})

it('findAllByDisplayValue', () => {
cy.findAllByDisplayValue(/^Display Value \d$/)
.should('have.length', 2)
})

it('findByAltText', () => {
cy.findByAltText('Image Alt Text 1').click()
})

it('findAllByAltText', () => {
cy.findAllByAltText(/^Image Alt Text \d$/).should('have.length', 2)
})

it('findByTitle', () => {
cy.findByTitle('Title 1').click()
})

it('findAllByTitle', () => {
cy.findAllByTitle(/^Title \d$/).should('have.length', 2)
})

it('findByRole', () => {
cy.findByRole('dialog').click()
})

it('findAllByRole', () => {
cy.findAllByRole(/^dialog/).should('have.length', 2)
})

it('findByTestId', () => {
cy.findByTestId('image-with-random-alt-tag-1').click()
})

it('findAllByTestId', () => {
cy.findAllByTestId(/^image-with-random-alt-tag-\d$/).should('have.length', 2)
})

/* Test the behaviour around these queries */

it('findByText with should(\'not.exist\')', () => {
cy.findAllByText(/^Button Text \d$/).should('exist')
cy.findByText('Non-existing Button Text', {timeout: 100}).should('not.exist')
})

it('findByText within', () => {
cy.get('#nested').within(() => {
cy.findByText('Button Text 2').click()
})
})

it('findByText in container', () => {
return cy.get('#nested')
.then(subject => {
cy.findByText(/^Button Text/, {container: subject}).click()
})
})

it('findByText works when another page loads', () => {
cy.findByText('Next Page').click()
cy.findByText('New Page Loaded').should('exist')
})

it('findByText should error if no elements are found', () => {
const regex = /Supercalifragilistic/
const errorMessage = `Timed out retrying: Expected to find element: 'findByText(${regex})', but never found it.`
cy.on('fail', err => {
expect(err.message).to.eq(errorMessage)
})

cy.findByText(regex, {timeout: 100}) // Doesn't explicitly need .should('exist') if it's the last element?
})

it('findByText finding multiple items should error', () => {
const errorMessage = `Found multiple elements with the text: /^Button Text/i\n\n(If this is intentional, then use the \`*AllBy*\` variant of the query (like \`queryAllByText\`, \`getAllByText\`, or \`findAllByText\`)).`
cy.on('fail', err => {
expect(err.message).to.eq(errorMessage)
})

cy.findByText(/^Button Text/i)
})
})

/* global cy */
26 changes: 26 additions & 0 deletions cypress/integration/get.spec.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
describe('get* queries should error', () => {
beforeEach(() => {
cy.visit('/')
})

const queryPrefixes = ['By', 'AllBy']
const queryTypes = ['LabelText', 'PlaceholderText', 'Text', 'DisplayValue', 'AltText', 'Title', 'Role', 'TestId']

queryPrefixes.forEach(queryPrefix => {
queryTypes.forEach(queryType => {
const obsoleteQueryName = `get${queryPrefix + queryType}`;
const preferredQueryName = `find${queryPrefix + queryType}`;
it(`${obsoleteQueryName} should error and suggest using ${preferredQueryName}`, () => {

const errorMessage = `You used '${obsoleteQueryName}' which has been removed from Cypress Testing Library because it does not make sense in this context. Please use '${preferredQueryName}' instead.`
cy.on('fail', err => {
expect(err.message).to.eq(errorMessage)
})

cy[`${obsoleteQueryName}`]('Irrelevant')
})
})
})
})

/* global cy */
Loading