# How to Debug Issues Within the Cypress Server: A Complete Guide

> Debug Cypress server issues effectively. Enable verbose logging with DEBUG=cypress:* and use Node's --inspect-brk to attach a debugger. Step through server code to find port conflicts or proxy failures.

- Repository: [Cypress.io/cypress](https://github.com/cypress-io/cypress)
- Tags: how-to-guide
- Published: 2026-06-21

---

**Set the `DEBUG=cypress:*` environment variable to enable verbose logging, then use Node's `--inspect-brk` flag to attach a debugger and step through the server lifecycle in [`packages/server/lib/server-base.ts`](https://github.com/cypress-io/cypress/blob/main/packages/server/lib/server-base.ts) to isolate port conflicts, proxy failures, or unexpected shutdowns.**

The Cypress server (located in `packages/server` within the `cypress-io/cypress` repository) orchestrates the HTTP server, file serving, HTTPS proxy, and WebSocket coordination that powers every test run. When you need to debug issues within the Cypress server, you must instrument its TypeScript source code directly, capture event emitter output, and leverage Node.js debugging tools to trace the asynchronous flow from server creation to socket handshake.

## Enable Verbose Logging with the DEBUG Environment Variable

The server uses the `debug` npm package to emit detailed runtime information via namespaces like `cypress:server*`. When you set the `DEBUG` environment variable, these messages appear in the console, revealing exactly when the HTTP server is created, when the file server starts, and when the HTTPS proxy is instantiated.

Set the variable to capture all server output:

```bash
DEBUG=cypress:* yarn dev

```

Or narrow the scope to server-specific logs only:

```bash
DEBUG=cypress:server* yarn cypress:run

```

Look for messages containing `createServer`, `ensuring baseUrl`, or `error on socket` to identify where the lifecycle breaks.

## Attach Node's Inspector for Step-by-Step Debugging

For failures that logging alone cannot explain, run Cypress with Node's inspector flag to pause execution and attach Chrome DevTools, VS Code, or WebStorm:

```bash
node --inspect-brk $(npm bin)/cypress open

```

Then connect your debugger to `ws://127.0.0.1:9229`. Set breakpoints inside `ServerBase.createServer` (around lines 70-90 in [`packages/server/lib/server-base.ts`](https://github.com/cypress-io/cypress/blob/main/packages/server/lib/server-base.ts)) to inspect the `config.port`, `config.baseUrl`, and the `_listen` result. If the server crashes during WebSocket upgrades, place a breakpoint in `ServerBase.onUpgrade` (around line 76) to examine the `req`, `socket`, and `head` objects.

## Instrument Key Source Files

Knowing where to place `console.log` statements or breakpoints requires familiarity with three core files that manage the server lifecycle.

### Server Lifecycle in server-base.ts

The [`packages/server/lib/server-base.ts`](https://github.com/cypress-io/cypress/blob/main/packages/server/lib/server-base.ts) file contains the `ServerBase` class, which is the primary orchestrator. Key methods include:

- **`ServerBase.createServer`** – Instantiates the HTTP server, file server, and HTTPS proxy (lines 70-90).
- **`ServerBase.onUpgrade`** – Handles WebSocket upgrade events (line 76).
- **`setupCrossOriginRequestHandling`** – Emits `error` and `warning` events via `this._eventBus`.

When debugging proxy-related issues, examine the HTTPS proxy creation at lines 94-98 and the `onRequest` / `onUpgrade` callbacks. The proxy logs are emitted via `debug('proxy request…')` in [`packages/server/lib/https-proxy.ts`](https://github.com/cypress-io/cypress/blob/main/packages/server/lib/https-proxy.ts).

### Project Management in project-base.ts

The [`packages/server/lib/project-base.ts`](https://github.com/cypress-io/cypress/blob/main/packages/server/lib/project-base.ts) file creates a `ServerBase` instance for each project and wires up lifecycle events. Use **`ProjectBase.open`** to trace server initialization and **`ProjectBase.reset`** to force a clean shutdown and recreation of the environment, clearing sockets and avoiding state leakage between runs.

### Configuration Resolution in config.ts

The server reads its final configuration from `cfg` in [`packages/server/lib/config.ts`](https://github.com/cypress-io/cypress/blob/main/packages/server/lib/config.ts). After `ProjectBase.open` resolves, log the final config to verify `port`, `proxyUrl`, `baseUrl`, `fileServerFolder`, and `socketIoCookie` values:

```ts
console.log('Final server config:', cfg)

```

## Capture Server Events and Configuration State

The server exposes an `EventEmitter` via `this._eventBus`. You can listen to `error` and `warning` events programmatically to capture stack traces that would otherwise be lost:

```ts
import { ProjectBase } from '@packages/server/lib/project-base'

const project = new ProjectBase({
  projectRoot: process.cwd(),
  options: { onError: console.error, onWarning: console.warn },
  testingType: 'e2e',
})

project.on('error', (err) => console.error('Server error:', err))
project.on('warning', (warn) => console.warn('Server warning:', warn))

await project.open()

```

This approach is particularly useful when `onError` or `onWarning` callbacks are not provided through the standard CLI interface.

## Run Tests in Headed Mode to Capture Runtime Errors

When a test fails because the server crashed, run Cypress with the `--headed` flag to keep the Electron or Chrome DevTools console open:

```bash
yarn cypress:run -- --headed --spec path/to/failing.spec.ts

```

A headed run displays the runner process console, including server `debug` output and network-proxy errors that are hidden in CI logs.

## Leverage Unit Tests for Reproduction Scenarios

The test suite under `packages/server/test/unit/` mirrors the production code and demonstrates expected lifecycle behavior. Key files include:

- **[`packages/server/test/unit/server-base_spec.ts`](https://github.com/cypress-io/cypress/blob/main/packages/server/test/unit/server-base_spec.ts)** – Shows how the server handles upgrades and HTTP/HTTPS proxy behavior.
- **[`packages/server/test/unit/project-base_spec.ts`](https://github.com/cypress-io/cypress/blob/main/packages/server/test/unit/project-base_spec.ts)** – Demonstrates opening, resetting, and closing a `ProjectBase` instance.

Replicating a failing test locally can isolate whether the issue stems from your configuration or the server internals.

## Practical Debugging Script

Create a temporary script (e.g., [`debug-server.ts`](https://github.com/cypress-io/cypress/blob/main/debug-server.ts) in the repo root) to programmatically start the server and attach event listeners:

```ts
import { ProjectBase } from '@packages/server/lib/project-base'
import { config } from '@packages/server/lib/config'

async function main () {
  const cfg = await config.readAndValidate({ /* …options … */ })
  const project = new ProjectBase({
    projectRoot: process.cwd(),
    options: { onError: console.error, onWarning: console.warn },
    testingType: 'e2e',
  })

  project.on('error', err => console.error('⚠️ Server error →', err))
  project.on('warning', warn => console.warn('🔔 Server warning →', warn))

  await project.open()
  
  console.log('🚀 Server listening on port', project.server?.address()?.port)
  
  // Keep the process alive for manual inspection
  await new Promise(() => {})
}

main().catch(err => console.error(err))

```

Run this with the inspector to step through the entire initialization flow:

```bash
node --inspect-brk debug-server.ts

```

## Summary

- **Use `DEBUG=cypress:*`** to surface verbose logs from the `debug` package in [`packages/server/lib/server-base.ts`](https://github.com/cypress-io/cypress/blob/main/packages/server/lib/server-base.ts).
- **Attach Node's `--inspect-brk`** to step through `ServerBase.createServer` and inspect `config.port`, `this._httpsProxy`, and `this._remoteStates`.
- **Listen to `error` and `warning` events** on `ProjectBase` instances to capture stack traces from `this._eventBus`.
- **Check [`packages/server/lib/config.ts`](https://github.com/cypress-io/cypress/blob/main/packages/server/lib/config.ts)** to verify final values for `port`, `baseUrl`, and `proxyUrl` after resolution.
- **Call `project.reset()`** to guarantee a clean state between debugging iterations.
- **Reference [`server-base_spec.ts`](https://github.com/cypress-io/cypress/blob/main/server-base_spec.ts)** to understand expected server behavior and edge-case handling.

## Frequently Asked Questions

### How do I filter debug output to show only server-related messages?

Set the `DEBUG` environment variable to `cypress:server*` instead of `cypress:*`. This namespace filters the output to only messages from `packages/server`, hiding browser driver logs and runner noise while preserving the HTTP server, proxy, and socket initialization logs.

### Which source file contains the main HTTP server creation logic?

The [`packages/server/lib/server-base.ts`](https://github.com/cypress-io/cypress/blob/main/packages/server/lib/server-base.ts) file contains the `ServerBase` class and its `createServer` method (around lines 70-90), which orchestrates the HTTP server, file server, HTTPS proxy, and GraphQL WebSocket instantiation. This is the primary entry point for server lifecycle debugging.

### How can I programmatically reset the server state during debugging?

Call `await project.reset()` on your `ProjectBase` instance. According to the source in [`packages/server/lib/project-base.ts`](https://github.com/cypress-io/cypress/blob/main/packages/server/lib/project-base.ts), this method shuts down the current server, clears sockets, and re-creates the environment, preventing state leakage between test runs while you iterate on a fix.

### What is the recommended way to debug proxy errors in the Cypress server?

Enable `DEBUG=cypress:server*` and set breakpoints in [`packages/server/lib/server-base.ts`](https://github.com/cypress-io/cypress/blob/main/packages/server/lib/server-base.ts) around lines 94-98 where the HTTPS proxy is created, and in [`packages/server/lib/https-proxy.ts`](https://github.com/cypress-io/cypress/blob/main/packages/server/lib/https-proxy.ts) where `debug('proxy request…')` is called. Inspect the `onRequest` and `onUpgrade` callbacks to see the exact request headers and TLS termination behavior.