Skip to main content

Experiments

If you'd like to try out what we're working on in Cypress, you can enable specific experimental features for your project using the Cypress configuration options described below.

caution

⚠️ The experimental features might change or ultimately be removed without making it into the core product. Our primary goal for experiments is to collect real-world feedback during their development. For more information, see the documentation for all Cypress Release Stages.

Configuration

You can pass the Cypress configuration options below to enable or disable experiments. See our Configuration Guide on how to pass configuration to Cypress.

OptionDefaultDescription
experimentalCspAllowListfalseIndicates the Content-Security-Policy directives to be permitted during a test run. See Content-Security-Policy for more information.
experimentalFetchPolyfillfalseAutomatically replaces window.fetch with a polyfill that Cypress can spy on and stub. Note: experimentalFetchPolyfill has been deprecated in Cypress 6.0.0 and will be removed in a future release. Consider using cy.intercept() to intercept fetch requests instead.
experimentalInteractiveRunEventsfalseAllows listening to the before:run, after:run, before:spec, and after:spec events in the setupNodeEvents function during interactive mode.
experimentalMemoryManagementfalseEnables support for improved memory management within Chromium-based browsers.
experimentalModifyObstructiveThirdPartyCodefalseWhether Cypress will search for and replace obstructive code in third party .js or .html files. NOTE: Setting this flag removes Subresource Integrity (SRI).
experimentalSourceRewritingfalseEnables AST-based JS/HTML rewriting. This may fix issues caused by the existing regex-based JS/HTML replacement algorithm. See #5273 for details.
experimentalWebKitSupportfalseEnable experimental support for running tests in WebKit. When set, installs of playwright-webkit will be detected and available in Cypress. See Launching Browsers for more information.
retries.experimentalStrategyN/AApplies a strategy for test retries according to your "flake tolerance"; options are detect-flake-but-always-fail or detect-flake-and-pass-on-threshold. See Experimental Retries for more details.
retries.experimentalOptionsN/ASets retries strategy-specific options like maxRetries, passesRequired, and stopIfAnyPassed. See Experimental Retries for more details.

Experimental CSP Allow List

Cypress by default strips all CSP headers (Content-Security-Policy and Content-Security-Policy-Report-Only) from the response before it is sent to the browser. The experimentalCspAllowList option allows for more granular control over which CSP directives are stripped from the CSP response headers, allowing you to test your application with CSP enabled. Valid values for this option are false (the default), true, or an array of CSP directive names.

ValueExample
false (default)experimentalCspAllowList=false
trueexperimentalCspAllowList=true
<CspDirectives>[]experimentalCspAllowList=["default-src","script-src"]

Strip All CSP Headers

The value experimentalCspAllowList=false (default) will remove all CSP headers from the response before it is sent to the browser. This option should be used if you do not depend on CSP for any tests in your application.

Strip Minimum CSP Directives

If you need to test your application with CSP enabled, setting the experimentalCspAllowList option will allow all CSP headers to be sent to the browser except those that could prevent Cypress from functioning normally.

The following CSP directives will always be stripped:

Stripped DirectiveAllowableReason
frame-ancestorsNoPrevents Cypress from loading a test application into an iframe.
navigate-toNoAffects Cypress' ability to navigate to different URLs.
require-trusted-types-forNoMight prevent Cypress from rewriting the DOM.
sandboxNoCan restrict access to script and iframe functionality.
trusted-typesNoCould cause Cypress injections to be marked as untrusted.

When experimentalCspAllowList=true the following directives are also stripped in addition to the ones listed above, but can be configured to be allowed to be sent to the browser:

Stripped DirectiveAllowableReason
child-srcYesCould prevent iframes from loading in combination with other Cypress options.
default-srcYesConditionally prevents Cypress from loading scripts and running.
frame-srcYesCould prevent iframes from loading in combination with other Cypress options.
form-actionYesCan prevent Cypress from monitoring form events.
script-srcYesConditionally prevents Cypress from loading scripts and running.
script-src-elemYesConditionally prevents Cypress from loading scripts and running.

Allow Specific CSP Directives

Set the experimentalCspAllowList option to an array of directive names marked as "Allowable" from the list above. This will allow the specified CSP directives to be sent to the browser.

The following configuration would allow the default-src, script-src, and script-src-elem directives to be sent to the browser:

const { defineConfig } = require('cypress')

module.exports = defineConfig({
experimentalCspAllowList: ['default-src', 'script-src', 'script-src-elem'],
})
caution

Defining experimentalCspAllowList may cause Cypress to be unable to run tests against your application. If you experience issues, reduce the directives specified in your allow list to identify which directive is causing issues.

There is a known issue when using certain directives containing hash algorithm values and the modifyObstructiveCode and/or experimentalSourceRewriting options. Using these options in combination with the experimentalCspAllowList option can cause a mismatch between the original hashed directive value, and the modified HTML or JS value.

Experimental Flake Detection Features

Experimental Test Retries

Test retries is a Cypress Flake Detection feature that enables you to re-attempt any tests that initially fail. The failure may not be a "true" failure, i.e. flaky. The only way to determine this is to retry the test.

Normally, test retries simply stop on the first passing attempt. And the final test result of any flaky test is always "passing", regardless of how many prior attempts failed. The following experimental settings for retries give you more control over the retries process.

There are two strategies for retries:

  • detect-flake-and-pass-on-threshold
  • detect-flake-but-always-fail

The detect-flake-and-pass-on-threshold strategy is most like the current implementation of retries, where failing tests have a "chance" to still pass, but still detect flake. But this new experimental strategy also enables you to now set a threshold of passing attempts to achieve a passing final result. And if you want to ensure flaky tests are treated with the same urgency as failing tests, then you will prefer to use the detect-flake-but-always-fail strategy, which assures that every flaky test is still marked as failing.

experimentalStrategy: 'detect-flake-and-pass-on-threshold'

Setting experimentalStrategy: 'detect-flake-and-pass-on-threshold' within retries will give you ability to set how many passing attempts are required for the test result to be passing. There are two experimentalOptions that must be set with this strategy:

  • maxRetries sets the maximum number of retries that can occur after the first attempt failed
  • passesRequired sets the required number of passing attempts for the final test result to be passing. Cannot be greater than maxRetries.
    • passesRequired also determines how the retries may stop before maxRetries is reached; either if the number of passing attempts so far has met the passesRequired condition or if the number of failing attempts exceeds the difference between maxRetries and passesRequired (when it's impossible to achieve the passing result).
const { defineConfig } = require('cypress')

module.exports = defineConfig({
retries: {
experimentalStrategy: 'detect-flake-and-pass-on-threshold',
experimentalOptions: {
maxRetries: 2,
passesRequired: 2,
},

// you must also explicitly set openMode and runMode to
// either true or false when using experimental retries
openMode: true,
runMode: true,
},
})

Examples of the above configuration's results:

Scenario 1:

  • Attempt 1: Fail
  • Attempt 2: Pass
  • Attempt 3: Fail

The retries stop on attempt 3, since maxRetries: 2 is now met and the test's final result is failing and flaky. Only one attempt passed, but two are needed to pass.

Scenario 2:

  • Attempt 1: Fail
  • Attempt 2: Pass
  • Attempt 3: Pass

Retries stop at attempt 3 again, and the test is passing and flaky, since there are now two passing attempts.

Scenario 3:

  • Attempt 1: Fail
  • Attempt 2: Fail

Retries stop on attempt 2, and the test is failing , because the requisite two passing attempts for a passing result can no longer be achieved once the 1st retry failed. It's also not flaky, since there were no passing attempts.

experimentalStrategy: 'detect-flake-but-always-fail'

Setting experimentalStrategy: 'detect-flake-but-always-fail' within retries ensures any test with any failed attempt will always end with a failing final result. There are two experimentalOptions that must be set in this strategy:

  • maxRetries sets the maximum number of retries that can occur after the first attempt failed
  • stopIfAnyPassed will stop the retries before maxRetries is reached when there is any passing attempt.
    • stopIfAnyPassed causes retries to exit as soon as any flake is detected (a test that is retrying after a failure only needs to pass once to exhibit flaky behavior). However it may help to see more retry attempts, such as when the failure mode is also non-deterministic and more of these different errors are revealed on more retries, in which case stopIfAnyPassed: false may be desirable.
const { defineConfig } = require('cypress')

module.exports = defineConfig({
retries: {
experimentalStrategy: 'detect-flake-but-always-fail',
experimentalOptions: {
maxRetries: 2,
stopIfAnyPassed: true,
},

// you must also explicitly set openMode and runMode to
// either true or false when using experimental retries
openMode: true,
runMode: true,
},
})

Examples of the above configuration's results:

Scenario 1:

  • Attempt 1: Fail
  • Attempt 2: Fail
  • Attempt 3: Fail

The retries stop on attempt 3, since maxRetries: 2 is now met and the test is failing , but also not flaky.

Scenario 2:

  • Attempt 1: Fail
  • Attempt 2: Pass

Retries stop on the first retry, due to the passing attempt. The test is failing and flaky. If stopIfAnyPassed was false, then the retries would have proceeded once more.

caution

Note: Experimental retries can only be configured at the global level and not per individual test, whereas non-experimental retries can be configured per test. If you configure retries on a per-test basis while using experimental retries globally, that particular test's retries configuration will override the experimental retries and ignore it.

Also, while using experimental retries, you cannot set numeric values for openMode or runMode at the global level. You can instead set true or false for each.

info

If you have any feedback for the experimental retries feature, please use this form.

Testing Type-Specific Experiments

You can provide configuration options for either E2E or Component Testing by creating e2e and component objects inside your Cypress configuration.

End-to-End Testing

These experiments are available to be specified inside the e2e configuration object:

OptionDefaultDescription
experimentalStudiofalseGenerate and save commands directly to your test suite by interacting with your app as an end user would.
experimentalRunAllSpecsfalseEnables the "Run All Specs" UI feature, allowing the execution of multiple specs sequentially.
experimentalOriginDependenciesfalseEnables support for Cypress.require within cy.origin.
experimentalSkipDomainInjectionnullRemoves injecting document.domain into text/html pages for any sites that match the provided patterns.

Experimental Skip Domain Injection

Under the hood, Cypress injects document.domain into your test application to lessen the burden of navigation. This is well described in our Cross Origin Testing guide. However, some sites have compatibility issues with this feature.

The experimentalSkipDomainInjection option disables injecting document.domain inside Cypress. When enabled, all cross-origin/subdomain navigation must use cy.origin(), which may make tests a bit more verbose. We only recommend including your site pattern if you are having issues running Cypress out of the box and suspect setting document.domain is interfering with your site's ability to render properly.

Before enabling, verify your application is not implementing frame busting techniques, which you can mitigate with the modifyObstructiveCode and experimentalModifyObstructiveThirdPartyCode flags.

At this point in time, we are aware of the following sites that require the experimentalSkipDomainInjection option to be set to be tested properly:

  • Google
  • Salesforce

This flag can be enabled by passing an array of origin URLs or minimatch glob patterns:

const { defineConfig } = require('cypress')

module.exports = defineConfig({
e2e: {
experimentalSkipDomainInjection: [
'*.salesforce.com',
'*.force.com',
'*.google.com',
],
},
})

If using other Salesforce domains, such as enhanced domains, you will need to add the correct matching glob pattern.

Component Testing

These experiments are available to be specified inside the component configuration object:

OptionDefaultDescription
experimentalSingleTabRunModefalseRun all specs in a single tab, instead of creating a new tab per spec. This can improve run mode performance, but can impact spec isolation and reliability on large test suites.
experimentalJustInTimeCompilefalseEnables Just-In-Time (JIT) compiling for component testing, which will only compile assets related to the spec before the spec is run. Currently supported for Vite and Webpack.

Experimental Just-In-Time Compile

By default, Cypress compiles all specs used by component testing before allowing any spec to run. This works fine for smaller projects most of the time.

However, as a component testing suite grows, the dev server (vite or webpack-dev-server, depending on your application) also grows with it. This can get to a point where the dev server grows so large that it consumes a large majority of CPU and memory resources, leading to:

  • Out Of Memory (OOM) errors.
  • chunk load error, specific to Webpack where parts of the bundle fail to load.
  • long run times while running component tests in CI in cypress run mode.
  • Unable to efficiently develop tests in cypress open mode because the initial and recompiling times for specs and related components are extremely long.
  • Inability to leverage Smart orchestration effectively to scale resources due to all assets being compiled into the dev server regardless of what specs are run.

The experimentalJustInTimeCompile option is designed to remedy this problem. Enabling this option will enable Just-In-Time (JIT) compiling for component testing, which will only compile assets and resources related to the spec before the spec is run. This is applicable in both open and run modes.

In open and run modes, the dev server will start up when the Cypress application starts with the component testing type, but will only compile the spec once it is selected or run. When a different spec is run, the different spec is then compiled, omitting the previously run spec from the dev server.

This makes developing your current spec much faster in open mode when it comes to initial compiling and recompiling, with a minor tradeoff being to recompile when you switch specs.

This also significantly reduces the memory requirements needed to run your tests in run mode, with a tradeoff being that your tests might run slightly slower since the dev server needs to recompile. If time is a factor, Smart orchestration can now be effectively used to parallelize your component testing runs on smaller infrastructure since the dev server only compiles what is needed to run the spec.

We are using experimentalJustInTimeCompile internally within Cypress for our larger component testing suites and have noticed significant reductions in memory when running cypress run mode and have gained significantly faster compile times when leveraging cypress open to develop our tests.

If you are using this experiment and would like to leave feedback, please comment on our github discussion.

History

VersionChanges
13.14.0Added support for configuring the Experimental Just-In-Time (JIT) Compiling for component testing via experimentalJustInTimeCompile.
13.4.0Added support for configuring the Experimental Flake Detection strategy via retries.experimentalStrategy and retries.experimentalOptions.
12.6.0Removed require/import and added Cypress.require for experimentalOriginDependencies.
12.4.0Added experimentalSkipDomainInjection and experimentalMemoryManagement.
12.0.0Removed experimentalSessionAndOrigin and made it the default behavior. Added experimentalOriginDependencies.
11.2.0Added experimentalRunAllSpecs.
10.8.0Added experimentalWebKitSupport.
10.6.0Added support for experimentalSingleTabRunMode.
10.4.0Added support for experimentalModifyObstructiveThirdPartyCode.
9.6.0Added support for experimentalSessionAndOrigin and removed experimentalSessionSupport.
8.2.0Added support for experimentalSessionSupport.
7.1.0Added support for experimentalInteractiveRunEvents.
7.0.0Removed experimentalComponentTesting and made it the default behavior.
6.7.0Removed experimentalRunEvents and made it the default behavior.
6.3.0Added support for experimentalStudio.
6.2.0Added support for experimentalRunEvents.
6.0.0Removed experimentalNetworkStubbing and made it the default behavior when using cy.intercept().
6.0.0Deprecated experimentalFetchPolyfill.
5.2.0Removed experimentalShadowDomSupport and made it the default behavior.
5.1.0Added support for experimentalNetworkStubbing.
5.0.0Removed experimentalGetCookiesSameSite and made it the default behavior.
4.9.0Added support for experimentalFetchPolyfill.
4.8.0Added support for experimentalShadowDomSupport.
4.6.0Added support for experimentalSourceRewriting.
4.5.0Added support for experimentalComponentTesting.
4.3.0Added support for experimentalGetCookiesSameSite.