Add tests to your VTEX IO app in an instant ๐
yarn add -D @vtex/test-tools @apollo/react-testing@3 react-intl@3
Add a new script to your react/package.json
:
{
"name": "my-io-app",
"scripts": {
"test": "vtex-test-tools test"
}
}
Add these lines to your .vtexignore
:
react/**/__tests__/**
react/**/__mocks__/**
react/**/__snapshots__/**
react/**/*.test.js
react/**/*.test.ts
react/**/*.test.tsx
Run in your terminal:
yarn test
If you're using TypeScript there are a few more steps.
Done! ๐
Under the hood, we use Jest, so you can pass Jest flags as parameters: read the docs.
The module react
makes it easy to test VTEX IO React apps.
import React from 'react'
import { render } from '@vtex/test-tools/react'
import HelloWorld from './HelloWorld'
test('should render the Hello!', () => {
const { getByText } = render(<HelloWorld />)
const element = getByText(/Hello!/)
expect(element).toBeDefined()
})
This module uses @testing-library/react
(RTL) under the hood, so most of its API is the same (read their docs here).
We added a few more features to the regular render
function from RTL, such as a graphql
and locale
option. You can see more about them
down below.
You can also test your custom hooks.
import { hooks } from '@vtex/test-tools/react'
import useCustomHook from './useCustomHook'
const { renderHook, act } = hooks
it('counter should be one', async () => {
const { result } = renderHook(() => useCustomHook())
// This waits for the useEffect hook to be triggered and mutate hook state
await act(() => Promise.resolve())
expect(result.current).toBe(1)
})
The module uses @react-testing-library/react-hooks
under the hood, to understand the reactHook function you can read its doc
We will automatically wrap your component with an IntlProvider
with your app's messages/en-US.json
messages.
You can change the default locale being used adding a config to your package.json
. Example:
{
"name": "my-awesome-io-app",
"vtexTestTools": {
"defaultLocale": "pt-BR"
}
}
If you want to change the locale just in a test, you may pass the locale
option. Example:
import React from 'react'
import { render } from '@vtex/test-tools/react'
import HelloWorld from './HelloWorld'
test('should render the example translated to portuguese', () => {
const { getByText } = render(<HelloWorld />, { locale: 'pt' })
const element = getByText(/Olรก!/)
expect(element).toBeDefined()
})
We automatically wrap your component with an Apollo's MockedProvider
.
You can pass your mocked queries to it using the graphql
option. Example:
import React from 'react'
import { render, flushPromises } from '@vtex/test-tools/react'
import GraphqlComponent from './GraphqlComponent'
import GET_BOOKS from './getBooks.graphql'
test('should render mock graphql responses', async () => {
jest.useFakeTimers()
const bookMock = {
request: {
query: GET_BOOKS,
},
result: {
data: {
books: [
{
id: 10,
title: 'Hello',
},
],
},
},
}
const { getByText } = render(<GraphqlComponent />, {
graphql: { mocks: [bookMock] },
})
expect(getByText(/Loading/)).toBeDefined()
await flushPromises()
jest.runAllTimers()
expect(getByText(/Hello/)).toBeDefined()
})
We offer hooks to make writing end-to-end tests easier.
Extended commands:
- clickById
- getById
- typeById
Custom methods:
- goToSearchPage
- goToProductPageByShelf
- checkText
- checkIfElementExists
- openCart
- closeCart
- clearCart
- fillAndCheckShippingSimulator
- scrollToId
Example:
import { openCart } from "@vtex/test-tools/cypress"
describe('Searchbar', () => {
before(() => {
cy.intercept(/operationName=ProductsSuggestionsQuery/, {
fixture: 'product-suggestions-query.json',
}).as('searchSuggestionsLoad')
})
it('finds a very specific product using the search bar', () => {
cy.visit('/')
cy.getById('searchBarInput').eq(0).type('Product')
cy.getById('searchSuggestionsItem').contains('Product').click()
cy.clickById('addToCart')
openCart()
...
})
})
You can check more details of these hooks in the links below:
These are some common use cases that might be helpful to see how it's done:
MIT ยฉ VTEX