Cypress 13 stabilised cy.session(), removed legacy cy.server()/cy.route(), and made component testing GA across React, Vue, Svelte, Angular. Config is TypeScript: cypress.config.ts with separate e2e and component blocks. cy.origin() handles cross-origin flows; cy.intercept() replaces everything network-related.
Install · configSetup
bash
# Install
npm i -D cypress
# Component testing also needs your framework adapter (auto-installed by the wizard):
# @cypress/react / @cypress/vue / @cypress/svelte / etc.
# Open the GUI (first run sets up cypress.config.ts + folders)
npx cypress open
# Run headlessly
npx cypress run # all e2e specs
npx cypress run --browser chrome # pick a browser
npx cypress run --component # component testing
npx cypress run --spec "cypress/e2e/auth/**" # path filter
npx cypress run --env tag=smoke # custom env var
npx cypress run --record --key $CY_KEY # to Cypress Cloud / Currents
# cypress.config.ts (minimum)
import { defineConfig } from "cypress";
export default defineConfig({
e2e: {
baseUrl: "http://localhost:3000",
setupNodeEvents(on, config) { return config; },
},
component: {
devServer: { framework: "react", bundler: "vite" },
},
video: false,
retries: { runMode: 2, openMode: 0 },
});
# package.json scripts
{
"scripts": {
"e2e": "cypress run",
"e2e:open": "cypress open",
"e2e:ci": "start-server-and-test dev http://localhost:3000 e2e"
}
}
Folders · filesProject layout
cypress.config.ts
Single config — e2e, component, env, retries.
cypress/e2e/**/*.cy.ts
E2E specs. Filename pattern is configurable.
cypress/component/**/*.cy.tsx
Component specs — mounted in a real browser.
cypress/fixtures/*.json
Static JSON loaded via cy.fixture() or in intercept.
cypress/support/e2e.ts
Loaded before every E2E spec — global hooks, plugin imports.
Assertions are retry-able: Cypress reruns the command + assertion until both pass or timeout expires. That’s why cy.get("...").should(...) beats cy.wait(500); cy.get("...").
Use data-testid or role queries, not CSS structure.
Class names and DOM shape change with refactors; data-testid + findByRole survive them.
Let retry-ability do the waiting.cy.get(".x").should("be.visible") retries until success or timeout. cy.wait(500) is a smell.
Seed via cy.request(), exercise via UI.
Logging in through the form for every test is slow and brittle. API-login + cy.session() is the standard pattern.
Common trapsWatch out for
Don’t await Cypress commands.
They’re queue entries, not promises. const x = await cy.get(...) yields the chain object, not the element.
Variables don’t flow through the chain.let user; cy.request(...).then(r => user = r.body); /* user is still undefined here */ — use .as("user") + cy.get("@user").
Cross-origin navigation throws.
Going to a different origin (auth IdP, third-party widget) requires cy.origin("https://...", () => ...), not a bare cy.visit().
Cypress is an end-to-end testing framework for web applications. It runs in the same process as the browser, giving you real-time access to the DOM, network requests, and application state. It supports both E2E tests that drive a full page and component tests that mount individual UI components.
Is Cypress better than Selenium?
Cypress is faster to set up and debug than Selenium because it runs in-process with the browser, has built-in automatic waiting, and comes with a time-travel debugger. Selenium is better when you need multi-tab control, cross-browser coverage beyond Chromium and Firefox, or non-JavaScript test runners.
Does Cypress support cross-origin testing?
Yes. Since Cypress 9.6, cy.origin() lets you navigate to a different domain in the same test and interact with it. You pass the origin as a string, then run commands inside the callback. The experimentalModifyObstructiveThirdPartyCode flag handles stubborn third-party auth pages.
How do I stub API calls in Cypress?
Use cy.intercept(method, url, response) to intercept and stub network requests. You can return a fixture file, an inline object, or a callback that modifies the real response. Always assign an alias with .as('alias') and wait on it with cy.wait('@alias') to synchronize the test.
Does Cypress support component testing?
Yes. Since Cypress 10, component testing is GA for React, Vue, Svelte, and Angular. Run cypress open --component or configure a separate component block in cypress.config.ts. Component tests mount a single component in a real browser without a server, giving fast, isolated feedback.
Is Cypress free and open source?
The Cypress test runner is MIT-licensed and free to use locally and in CI. Cypress Cloud (formerly Cypress Dashboard) is the paid SaaS product for parallelization, test recording, flake detection, and analytics — it has a limited free tier. All core testing functionality including component testing, network interception, and the Test Replay feature in recent versions is available without a subscription.