Skip to content

12: update test isolation docs to use true/false instead of on/off #4890

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 9 commits into from
Dec 5, 2022
4 changes: 4 additions & 0 deletions content/_data/sidebar.json
Original file line number Diff line number Diff line change
Expand Up @@ -197,6 +197,10 @@
"title": "Writing and Organizing Tests",
"slug": "writing-and-organizing-tests"
},
{
"title": "Test Isolation",
"slug": "test-isolation"
},
{
"title": "Retry-ability",
"slug": "retry-ability"
Expand Down
41 changes: 21 additions & 20 deletions content/api/commands/session.md
Original file line number Diff line number Diff line change
Expand Up @@ -12,8 +12,8 @@ tests.

The `cy.session()` command will inherit the
[`testIsolation`](/guides/core-concepts/writing-and-organizing-tests#Test-Isolation)
mode value to determine whether or not the page is cleared when caching and
restoring the browser context.
value to determine whether or not the page is cleared when caching and restoring
the browser context.

## Syntax

Expand Down Expand Up @@ -102,11 +102,11 @@ runs, Cypress will preserve all cookies, `sessionStorage`, and `localStorage`,
so that subsequent calls to `cy.session()` with the same `id` will bypass
`setup` and just restore the cached session data.

The page is cleared before `setup` when `testIsolation='on'` and is not cleared
when `testIsolation='off'`.
The page is cleared before `setup` when `testIsolation` is enabled and is not
cleared when `testIsolation` is disabled.

Cookies, local storage and session storage in all domains are always cleared
before `setup` runs, regardless of the testIsolation configuration.
before `setup` runs, regardless of the `testIsolation` configuration.

**<Icon name="angle-right"></Icon> options** **_(Object)_**

Expand Down Expand Up @@ -645,13 +645,13 @@ it('t3', () => {

### When the page and session data are cleared

### Test Isolation `on`
### Test Isolation Enabled

The page is cleared and cookies, local storage and session storage (session
data) in all domains are cleared automatically when `cy.session()` runs and
`testIsolation` is `on`. This guarantees consistent behavior whether a session
is being created or restored and allows you to switch sessions without first
having to explicitly log out.
data) in all domains are cleared automatically when `cy.session()` runs and test
isolation is enabled with `testIsolation=true`, This guarantees consistent
behavior whether a session is being created or restored and allows you to switch
sessions without first having to explicitly log out.

| | Page cleared (test) | Session data cleared |
| -------------------------- | :---------------------------------------------: | :---------------------------------------------: |
Expand All @@ -661,10 +661,10 @@ having to explicitly log out.
[`cy.visit()`](/api/commands/visit) must be explicitly called afterwards to
ensure the page to test is loaded.

### Test Isolation `off`
### Test Isolation Disabled

When `testIsolation` is `off`, the page will not clear, however, the session
data will clear when `cy.session()` runs.
When test isolation is disabled with `testIsolation=false`, the page will not
clear, however, the session data will clear when `cy.session()` runs.

| | Page cleared (test) | Session data cleared |
| -------------------------- | :-----------------: | :---------------------------------------------: |
Expand All @@ -674,13 +674,13 @@ data will clear when `cy.session()` runs.
[`cy.visit()`](/api/commands/visit) does not need to be called afterwards to
ensure the page to test is loaded.

NOTE: Turning test isolation off may improve performance of end-to-end tests,
NOTE: Disabling test isolation may improve performance of end-to-end tests,
however, previous tests could impact the browser state of the next test and
cause inconsistency when using .only(). Be mindful to write isolated tests when
test isolation is off.
test isolation is disabled.

When test isolation is `off`, it is encouraged to setup your session in a before
hook or in the first test to ensure a clean setup.
When test isolation is disabled, it is encouraged to setup your session in a
before hook or in the first test to ensure a clean setup.

### Session caching

Expand Down Expand Up @@ -823,9 +823,10 @@ generate random unique ids if an arbitrary name-space does not meet your needs.

#### Why are all my Cypress commands failing after calling `cy.session()`?

When test isolation is `on`, ensure that you're calling
[`cy.visit()`](/api/commands/visit) after calling `cy.session()`, otherwise your
tests will be running on a blank page.
When
[`testIsolation`](/guides/core-concepts/writing-and-organizing-tests#Test-Isolation)
is enabled, ensure that you're calling [`cy.visit()`](/api/commands/visit) after
calling `cy.session()`, otherwise your tests will be running on a blank page.

#### Why am I seeing `401` errors after calling `cy.session()`?

Expand Down
124 changes: 124 additions & 0 deletions content/guides/core-concepts/test-isolation.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,124 @@
---
title: 'Test Isolation'
---

<Alert type="info">

## <Icon name="graduation-cap"></Icon> What you'll learn

- What is test isolation
- How it impacts E2E Testing vs Component Testing
- Test isolation trade-offs

</Alert>

## What is Test Isolation?

<Alert type="success">

<Icon name="check-circle" color="green"></Icon> **Best Practice:** Tests should
always be able to be run independently from one another **and still pass**.

</Alert>

As stated in our mission, we hold ourselves accountable to champion a testing
process that actually works, and have built Cypress to guide developers towards
writing independent tests from the start.

We do this by cleaning up state _before_ each test to ensure that the operation
of one test does not affect another test later on. The goal for each test should
be to **reliably pass** whether run in isolation or consecutively with other
tests. Having tests that depend on the state of an earlier test can potentially
cause nondeterministic test failures which make debugging challenging.

Cypress will start each test with a clean test slate by restoring and clearing
all:

- [aliases](/api/commands/as)
- [clock mocks](/api/commands/clock)
- [intercepts](/api/commands/intercept)
- [routes](/api/commands/route)
- [spies](/api/commands/spy)
- [stubs](/api/commands/stub)
- [viewport changes](/api/commands/viewport)

In additional to a clean test slate, Cypress also believes in running tests in a
clean browser context such that the application or component under test behaves
consistently when ran. This behavior is described as `testIsolation`.

The test isolation is a global configuration and can be overridden for
end-to-end testing at the `describe` level with the
[`testIsolation`](/guides/references/configuration#Global) option.

## Test Isolation in End-to-End Testing

Cypress supports enabling or disabling test isolation in end-to-end testing to
describe if a suite of tests should run in a clean browser context or not.

### Test Isolation Enabled

When test isolation is enabled, Cypress resets the browser context _before_ each
test by:

- clearing the dom state by visiting `about:blank`
- clearing [cookies](/api/cypress-api/cookies) in all domains
- clearing
[`localStorage`](https://developer.mozilla.org/en-US/docs/Web/API/Window/localStorage)
in all domains
- clearing
[`sessionStorage`](https://developer.mozilla.org/en-US/docs/Web/API/Window/sessionStorage)
in all domains

Because the test starts in a fresh browser context, you must re-visit your
application and perform the series of interactions needed to build the dom and
browser state for each test.

Additionally, the [`cy.session()`](/api/commands/session) command will inherent
this configuration and will clear the page and current browser context when
establishing a browser session. This is so tests can reliably pass when run
standalone or in a randomized order.

### Test Isolation Disabled

When test isolation is disabled, Cypress will not alter the browser context
before the test starts. The page does not clear between tests and cookies, local
storage and session storage will be available across tests in that suite.
Additionally, the [`cy.session()`](/api/commands/session) command will only
clear the current browser context when establishing the browser session - the
current page is not cleared.

### Quick Comparison

| testIsolation | beforeEach test | cy.session() |
| ------------- | ------------------------------------------------------------------------------------------------------------------------------------------------ | ------------------------------------------------------------------------------------------------------------------------------------------------ |
| `true` | - clears page by visiting `about:blank`<br>- clears cookies in all domains<br>- local storage in all domains<br>- session storage in all domains | - clears page by visiting `about:blank`<br>- clears cookies in all domains<br>- local storage in all domains<br>- session storage in all domains |
| `false` | does not alter the current browser context | <br>- clears cookies in all domains<br>- local storage in all domains<br>- session storage in all domains |

## Test Isolation in Component Testing

Cypress does not support configuring the test isolation behavior in component
testing.

When running component tests, Cypress always resets the browser context _before_
each test by:

- unmounting the rendered component under test
- clearing [cookies](/api/cypress-api/cookies) in all domains
- clearing
[`localStorage`](https://developer.mozilla.org/en-US/docs/Web/API/Window/localStorage)
in all domains
- clearing
[`sessionStorage`](https://developer.mozilla.org/en-US/docs/Web/API/Window/sessionStorage)
in all domains

## Test Isolation Trade-offs

It is important to note that disabling test isolation may improve the overall
performance of end-to-end tests, however, it can also cause state to "leak"
between tests. This can make later tests dependent on the results of earlier
tests, and potentially cause misleading test failures. It is important to be
extremely mindful of how tests are written when using this mode, and ensure that
tests continue to run independently of one another.

The best way to ensure your tests are independent is to add a `.only()` to your
test and verify it can run successfully without the test before it.
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

likely need to add an example here -- same as migration guide?

105 changes: 16 additions & 89 deletions content/guides/core-concepts/writing-and-organizing-tests.md
Original file line number Diff line number Diff line change
Expand Up @@ -575,95 +575,22 @@ As stated in our mission, we hold ourselves accountable to champion a testing
process that actually works, and have built Cypress to guide developers towards
writing independent tests from the start.

We do this by cleaning up state _before_ each test to ensure that the operation
of one test does not affect another test later on. The goal for each test should
be to **reliably pass** whether run in isolation or consecutively with other
tests. Having tests that depend on the state of an earlier test can potentially
cause nondeterministic test failures which makes debugging challenging.

Cypress will start each test with a clean test slate by restoring and clearing
all:

- [aliases](/api/commands/as)
- [clock mocks](/api/commands/clock)
- [intercepts](/api/commands/intercept)
- [routes](/api/commands/route)
- [spies](/api/commands/spy)
- [stubs](/api/commands/stub)
- [viewport changes](/api/commands/viewport)

In additional to a clean test slate, Cypress also believes in running tests in a
clean browser context such that the application or component under test behaves
consistently when ran. This concept is described as `testIsolation`.

The test isolation mode is a global configuration and can be overridden at the
`describe` level with the
[`testIsolation`](/guides/references/configuration#Global) option.

#### End-to-end testing

Cypress supports the following modes of test isolation in end-to-end testing to
describe if a suite of tests should run in a clean browser context or not: `on`
and `off`.

###### On Mode

This is the default test isolation behavior in Cypress. When in `on` mode,
Cypress resets the browser context _before_ each test by:

- clearing the dom state by visiting `about:blank`
- clearing [cookies](/api/cypress-api/cookies) in all domains
- clearing
[`localStorage`](https://developer.mozilla.org/en-US/docs/Web/API/Window/localStorage)
in all domains
- clearing
[`sessionStorage`](https://developer.mozilla.org/en-US/docs/Web/API/Window/sessionStorage)
in all domains

Because the test starts in a fresh browser context, you must re-visit your
application and perform the series of interactions needed to build the dom and
browser state for each test.

Additionally, the `cy.session()` command will inherent this mode and will clear
the page and current browser context when establishing a browser session. This
is so tests can reliably pass when run standalone or in a randomized order.

###### Off Mode

When in `off` mode, Cypress will not alter the browser context before the test
starts. The page does not clear between tests and cookies, local storage and
session storage will be available across tests in that suite. Additionally, the
`cy.session()` command will only clear the current browser context when
establishing the browser session - the current page will not clear.

It is important to note that while turning test isolation `off` may improve the
overall performance of end-to-end tests, it can however cause state to "leak"
between tests. This can make later tests dependent on the results of earlier
tests, and potentially cause misleading test failures. It is important to be
extremely mindful of how tests are written when using this mode, and ensure that
tests continue to run independently of one another.

###### Mode Comparison

| testIsolation | beforeEach test | cy.session() |
| ------------- | ------------------------------------------------------------------------------------------------------------------------------------------------ | ------------------------------------------------------------------------------------------------------------------------------------------------ |
| `on` | - clears page by visiting `about:blank`<br>- clears cookies in all domains<br>- local storage in all domains<br>- session storage in all domains | - clears page by visiting `about:blank`<br>- clears cookies in all domains<br>- local storage in all domains<br>- session storage in all domains |
| `off` | does not alter the current browser context | <br>- clears cookies in all domains<br>- local storage in all domains<br>- session storage in all domains |

##### Component testing

Cypress only support testIsolation `on` in component testing.

When running component tests, Cypress resets the browser context _before_ each
test by:

- clearing the page
- clearing [cookies](/api/cypress-api/cookies)
- clearing
[`localStorage`](https://developer.mozilla.org/en-US/docs/Web/API/Window/localStorage)
- clearing
[`sessionStorage`](https://developer.mozilla.org/en-US/docs/Web/API/Window/sessionStorage)
in all domains
We do this by cleaning up test state and the browser context _before_ each test
to ensure that the operation of one test does not affect another test later on.
The goal for each test should be to **reliably pass** whether run in isolation
or consecutively with other tests. Having tests that depend on the state of an
earlier test can potentially cause nondeterministic test failures which makes
debugging challenging.

The behavior of running tests in a clean browser context is described as
`testIsolation`.

The test isolation is a global configuration and can be overridden for
end-to-end testing at the `describe` level with the
[`testIsolation`](/guides/references/configuration#e2e) option.

To learn more about this behavior and the trade-offs of disabling it, review our
[Test Isolation guide](/guides/core-concepts/test-isolation).

### Test Configuration

Expand Down
2 changes: 1 addition & 1 deletion content/guides/references/configuration.md
Original file line number Diff line number Diff line change
Expand Up @@ -208,7 +208,7 @@ object:
| `specPattern` | `cypress/e2e/**/*.cy.{js,jsx,ts,tsx}` | A String or Array of glob patterns of the test files to load. |
| `excludeSpecPattern` | `*.hot-update.js` | A String or Array of glob patterns used to ignore test files that would otherwise be shown in your list of tests. [Please read the notes on using this.](#excludeSpecPattern) |
| `slowTestThreshold` | `10000` | Time, in milliseconds, to consider a test "slow" during `cypress run`. A slow test will display in orange text in the default reporter. |
| `testIsolation` | `on` | The [test isolation level](/guides/core-concepts/writing-and-organizing-tests#Test-Isolation) applied to ensure a clean slate between tests. Options are `on` or `off`. |
| `testIsolation` | `true` | Whether or not [test isolation](/guides/core-concepts/writing-and-organizing-tests#Test-Isolation) is enabled to ensure a clean browser context between tests. |
| Option | Default | Description |
| `experimentalRunAllSpecs` | `false` | Enables the "Run All Specs" UI feature, allowing the execution of multiple specs sequentially. |

Expand Down
Loading