# How the Cypress Driver Executes Commands and Manages the Test Runtime in the Browser

> Learn how the Cypress driver executes commands and manages test runtime in the browser. Discover its `cy` API to `$Command` object conversion, queuing, and retry mechanisms.

- Repository: [Cypress.io/cypress](https://github.com/cypress-io/cypress)
- Tags: internals
- Published: 2026-07-12

---

**The Cypress driver is a self‑contained single‑page JavaScript application running inside the browser that converts `cy` API calls into `$Command` objects, queues them in a `CommandQueue`, and automatically retries queries until assertions pass or the command timeout expires.**

The driver lives in the `@packages/driver` package of the [cypress-io/cypress](https://github.com/cypress-io/cypress) repository. It bootstraps the test environment, provides the `cy` API, and synchronizes state with the Cypress server while remaining entirely within the browser context.

## Core Architecture

The driver is organized into distinct layers that handle bootstrapping, command queuing, execution, and DOM interaction.

### Bootstrap Layer

Located in [`src/main.ts`](https://github.com/cypress-io/cypress/blob/main/src/main.ts), this layer loads polyfills, attaches telemetry, and exports the `$Cypress` singleton that initializes the entire driver instance.

### Command Queue

Implemented in [`src/cypress/command_queue.ts`](https://github.com/cypress-io/cypress/blob/main/src/cypress/command_queue.ts), the `CommandQueue` class stores `$Command` objects, inserts nested commands at the correct index, resolves retries, and finalizes error logs.

### Command Object

Defined in [`src/cypress/command.ts`](https://github.com/cypress-io/cypress/blob/main/src/cypress/command.ts), the `$Command` class represents a single Cypress command (e.g., `cy.visit()`, `cy.get()`). It holds metadata, manages state transitions (`queued → pending → passed/failed`), and generates unique IDs for cross‑origin tracking.

### Command Runner

Found in [`src/cypress/runner.ts`](https://github.com/cypress-io/cypress/blob/main/src/cypress/runner.ts), the runner pulls the next command from the queue, invokes the command’s implementation, and wires up retry logic via `cy.verifyUpcomingAssertions`.

### Command Implementations

Concrete behaviors live under `src/cy/commands/*`. For example, [`src/cy/commands/window.ts`](https://github.com/cypress-io/cypress/blob/main/src/cy/commands/window.ts) handles window navigation and [`src/cy/commands/xhr.ts`](https://github.com/cypress-io/cypress/blob/main/src/cy/commands/xhr.ts) manages network requests. These modules receive the resolved subject and perform the actual DOM or network actions.

### Stability Engine

[`src/cy/stability.ts`](https://github.com/cypress-io/cypress/blob/main/src/cy/stability.ts) detects when the page is idle by monitoring pending timers, in‑flight XHRs, and page load events, pausing the queue while the application is "unstable."

## The Command Lifecycle

When a test calls `cy.visit('/login')`, the driver moves the command through seven distinct stages.

### 1. Enqueue and Command Creation

The `cy` API registers commands via `Cypress.Commands.add` (defined in [`src/cypress/commands.ts`](https://github.com/cypress-io/cypress/blob/main/src/cypress/commands.ts)). Each call instantiates a `$Command` with a name, arguments, and chainer ID, then pushes it onto the `CommandQueue`.

```javascript
// e2e/spec.cy.js
describe('My app', () => {
  it('loads the page', () => {
    cy.visit('/login')            // → creates a $Command (type: 'visit')
    cy.get('input[name=user]')   // → creates a $Command (type: 'get')
    cy.type('admin')              // → creates a $Command (type: 'type')
  })
})

```

### 2. Nested Command Insertion

Custom commands that spawn sub‑commands set `state('nestedIndex')`. The `CommandQueue.enqueue` method uses this index to insert the new command immediately after its parent, ensuring proper execution order.

### 3. Run Loop Execution

`CommandQueue.run` (bound in the constructor) continuously dequeues the next pending command and invokes the implementation defined in `src/cy/commands/*`.

```js
// Inside the driver (simplified)
const cmd = new $Command({ name: 'visit', args: ['/login'] })
queue.enqueue(cmd)               // ← CommandQueue.enqueue (adds to queue)
queue.run()                      // ← CommandQueue.run loops until queue empty

```

### 4. Retry Query for Assertions

For query commands like `cy.get()`, the driver enters a retry loop. The `retryQuery` function (lines 73‑112 of [`command_queue.ts`](https://github.com/cypress-io/cypress/blob/main/command_queue.ts)) repeatedly invokes the user‑provided function until it returns a valid subject or times out.

```js
// Inside command_queue.ts → retryQuery
const onRetry = () => {
  return cy.verifyUpcomingAssertions(undefined, options, {
    onRetry,
    subjectFn: () => {
      const subject = cy.subject(command.get('chainerId'))
      Cypress.ensure.isType(subject, command.get('prevSubject'), command.get('name'), cy)
      return ret(subject)                 // ret is the user‑provided query fn
    },
  })
}

```

If `ret(subject)` throws or returns a falsy value, `verifyUpcomingAssertions` schedules another attempt until the timeout elapses.

### 5. Execution

The command’s implementation receives the resolved subject and performs the action (DOM manipulation, network request, etc.).

### 6. Logging and Error Handling

Each command creates log objects via `Cypress.log`. If a command throws, `CommandQueue.commandRunningFailed` (lines 22‑63) finalizes the error log with console properties and snapshots.

```js
// Inside command_queue.ts → commandRunningFailed
if (lastLog && !lastLog.get('ended')) {
  return lastLog.set({ consoleProps }).error(err)
}
return Cypress.log({ end: true, snapshot: true, error: err, consoleProps })

```

Successful commands call `CommandQueue.Command.finishLogs` (lines 60‑79) to mark logs complete.

### 7. State Transition

The `$Command` instance updates its internal state from `pending` to `passed` or `failed`, notifying the UI via the log system.

## Test Runtime Management

### Subject Passing and Chainer IDs

Cypress stores the subject of each command in the `cy` object accessible via `cy.subject()`. The `CommandQueue` uses the chainer ID to retrieve the correct subject for the next command in the chain, ensuring that `cy.get().type()` passes the DOM element through correctly.

### Automatic Retries and Timeouts

The driver reads the global timeout from `command.get('timeout')`. While a command’s assertions fail, the runner re‑invokes the query function until it passes or the timeout expires, providing the retry‑until‑pass behavior without explicit waits.

### Stability Detection

Before running most commands, the driver checks [`src/cy/stability.ts`](https://github.com/cypress-io/cypress/blob/main/src/cy/stability.ts) to ensure the page is idle. If timers are pending or XHRs are in flight, the queue pauses, preventing flaky interactions with unstable DOM elements.

### Cross‑Origin Command Tracking

When tests span multiple origins, each command receives a unique identifier generated in [`src/cypress/command.ts`](https://github.com/cypress-io/cypress/blob/main/src/cypress/command.ts):

```javascript
attrs.id = `${attrs.chainerId}-cmd-${idCounter++}`

```

This prevents ID collisions when commands are forwarded from a secondary origin back to the primary origin for logging and state synchronization.

## Key Implementation Files

- **[`src/main.ts`](https://github.com/cypress-io/cypress/blob/main/src/main.ts)** – Bootstrap entry point that initializes the driver.
- **[`src/cypress/command.ts`](https://github.com/cypress-io/cypress/blob/main/src/cypress/command.ts)** – `$Command` class definition and state machine.
- **[`src/cypress/command_queue.ts`](https://github.com/cypress-io/cypress/blob/main/src/cypress/command_queue.ts)** – Queue logic, retry handling, and error finalization.
- **[`src/cypress/runner.ts`](https://github.com/cypress-io/cypress/blob/main/src/cypress/runner.ts)** – Core run loop that executes dequeued commands.
- **[`src/cy/stability.ts`](https://github.com/cypress-io/cypress/blob/main/src/cy/stability.ts)** – Page stability detection and pause/resume logic.
- **`src/cy/commands/*`** – Concrete implementations for every `cy` command.
- **`src/dom/*`** – Thin wrappers over `document`, `window`, and Shadow DOM utilities.
- **[`src/util/commandAUTCommunication.ts`](https://github.com/cypress-io/cypress/blob/main/src/util/commandAUTCommunication.ts)** – Messaging between the driver and the Cypress server.

## Summary

- The **Cypress driver** is a browser‑based SPA in `@packages/driver` that powers the `cy` API.
- Commands are encapsulated as **`$Command`** objects and managed by the **`CommandQueue`** in [`src/cypress/command_queue.ts`](https://github.com/cypress-io/cypress/blob/main/src/cypress/command_queue.ts).
- **Retry logic** is handled by `retryQuery` and `verifyUpcomingAssertions`, which re‑invoke queries until timeouts expire.
- **Stability detection** in [`src/cy/stability.ts`](https://github.com/cypress-io/cypress/blob/main/src/cy/stability.ts) pauses execution while the page is loading or processing.
- **Cross‑origin safety** is ensured by unique command IDs generated with the pattern `${chainerId}-cmd-${counter}`.

## Frequently Asked Questions

### What is the Cypress driver and where does it execute?

The Cypress driver is the `@packages/driver` JavaScript package that runs as a single‑page application inside the browser frame alongside your application under test. It provides the `cy` API, manages the command queue, and communicates with the Cypress desktop application via `postMessage` and WebSocket connections.

### How does the CommandQueue handle automatic retries?

The `CommandQueue` calls `retryQuery` (defined in [`src/cypress/command_queue.ts`](https://github.com/cypress-io/cypress/blob/main/src/cypress/command_queue.ts)), which wraps the user’s query function in `cy.verifyUpcomingAssertions`. If the assertion fails or the subject is invalid, the engine schedules another attempt using the `onRetry` callback until the command’s timeout expires.

### Where does Cypress generate unique identifiers for commands crossing origins?

Unique IDs are generated in [`src/cypress/command.ts`](https://github.com/cypress-io/cypress/blob/main/src/cypress/command.ts) using the pattern `` `${attrs.chainerId}-cmd-${idCounter++}` ``. This ensures that when a command is created in a secondary origin and forwarded back to the primary origin for logging, it carries a globally unique identifier that prevents collisions in the queue.

### How does Cypress know when the page is stable before executing commands?

The driver uses [`src/cy/stability.ts`](https://github.com/cypress-io/cypress/blob/main/src/cy/stability.ts) to monitor pending timers, active XHR requests, and document load states. If the page is "unstable," the command queue pauses execution, resuming only once the stability detector reports that the application has reached an idle state.