Skip to content

Disable WebSocket by default (opt-in via ENABLE_WEBSOCKET)#3

Open
nanehambardzumyan wants to merge 2 commits into
mainfrom
cursor/disable-websocket-867a
Open

Disable WebSocket by default (opt-in via ENABLE_WEBSOCKET)#3
nanehambardzumyan wants to merge 2 commits into
mainfrom
cursor/disable-websocket-867a

Conversation

@nanehambardzumyan

@nanehambardzumyan nanehambardzumyan commented Jun 26, 2026

Copy link
Copy Markdown
Contributor

Summary

The API Simulator UI communicates over plain HTTP and does not use WebSockets — the /ws channel and POST /message broadcasting were a template-level feature that the simulator never relies on. This change disables WebSocket support by default and makes it opt-in.

Changes

  • server.js: WebSocket support is now gated behind ENABLE_WEBSOCKET. By default the ws module is not loaded, the /ws server is not started, and POST /message returns 503. Set ENABLE_WEBSOCKET=true to restore the previous behavior.
  • client/app.js: The browser no longer opens a WebSocket connection to /ws (and no longer enters the 3s reconnect loop). Re-enable by flipping the ENABLE_WEBSOCKET constant and running the server with ENABLE_WEBSOCKET=true.
  • vite.config.js: Removed the /ws dev-server proxy. With the backend WS server disabled, this proxy pointed at a dead upstream and produced repeated [vite] ws proxy error: write EPIPE spam whenever any (e.g. stale/cached) client tried to open /ws. Restore this entry if re-enabling WebSocket.

Testing

  • node scripts/smoke-test.mjs — demo CRUD still passes
  • curl -X POST http://localhost:3001/message503 (disabled by default)
  • ENABLE_WEBSOCKET=true PORT=3009 node server.jsPOST /message returns 200 and /ws server starts (re-enable works)
  • ✅ Simulated repeated stray /ws connection attempts against the Vite dev server → 0 EPIPE / ws-proxy errors (previously spammed every ~3s)
  • ✅ Remaining HTTP proxies intact: GET http://localhost:3000/demo-api/health200, frontend /200
  • ✅ Browser: console shows no WebSocket logs/errors, Network WS filter shows 0 connection attempts, and the simulator still returns 200 OK for GET /demo-api/health

Network WS filter shows 0 WebSocket connections
Simulator returns 200 OK with WebSocket disabled

To show artifacts inline, enable in settings.

Open in Web Open in Cursor 

cursoragent and others added 2 commits June 26, 2026 16:17
Co-authored-by: Nane Hambardzumyan <nanehambardzumyan@users.noreply.github.com>
Co-authored-by: Nane Hambardzumyan <nanehambardzumyan@users.noreply.github.com>
@nanehambardzumyan nanehambardzumyan marked this pull request as ready for review June 27, 2026 07:59
@coderabbitai

coderabbitai Bot commented Jun 27, 2026

Copy link
Copy Markdown

Review Change Stack

📝 Walkthrough

Walkthrough

The PR adds an ENABLE_WEBSOCKET gate in server startup, leaving websocket support disabled unless the env var is set. The client now only calls initializeWebSocket() when the flag is true, and the Vite proxy configuration removes the /ws websocket route.

🚥 Pre-merge checks | ✅ 4
✅ Passed checks (4 passed)
Check name Status Explanation
Title check ✅ Passed The title clearly summarizes the main change: WebSocket support is disabled by default and made opt-in.
Description check ✅ Passed The description is directly related to the changeset and accurately explains the WebSocket opt-in behavior.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.

Comment @coderabbitai help to get the list of available commands.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Actionable comments posted: 2

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@client/app.js`:
- Around line 4-7: The browser-side gate in client/app.js is hardcoded off, so
the optional messaging path can never be re-enabled even when the server/runtime
flag is set. Update the ENABLE_WEBSOCKET constant to read from shared
runtime/build configuration instead of using a literal false, and keep the
existing WebSocket connection setup in app.js driven by that shared flag so the
opt-in flow works end to end.

In `@server.js`:
- Around line 26-29: The WebSocket gating in server.js conflates
configuration-disabled and dependency-missing states via isWebSocketAvailable,
so split the logic around WEBSOCKET_ENABLED and the ws import in the startup
block and POST /message handler. Keep a separate flag or branch for “disabled by
config” versus “ws unavailable,” and return a distinct 503 response for each
case so clients only see the install-ws message when the dependency is actually
missing.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: 448c57d2-6a85-4db7-986c-44fd3b5ad1a7

📥 Commits

Reviewing files that changed from the base of the PR and between e15a35b and 40b3b95.

📒 Files selected for processing (3)
  • client/app.js
  • server.js
  • vite.config.js
💤 Files with no reviewable changes (1)
  • vite.config.js

Comment thread client/app.js
Comment on lines +4 to +7
// WebSocket messaging is disabled by default. The API Simulator UI uses plain
// HTTP, so the optional alert/messaging channel is opt-in. Set this to true and
// run the server with ENABLE_WEBSOCKET=true to re-enable it.
const ENABLE_WEBSOCKET = false;

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🎯 Functional Correctness | 🟠 Major | ⚡ Quick win

Don't hardcode the client gate to false.

With this literal, enabling ENABLE_WEBSOCKET=true on the server still never re-enables the browser connection, so the opt-in flow described in this PR cannot work end to end. Read the flag from shared runtime/build config instead of baking in false.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@client/app.js` around lines 4 - 7, The browser-side gate in client/app.js is
hardcoded off, so the optional messaging path can never be re-enabled even when
the server/runtime flag is set. Update the ENABLE_WEBSOCKET constant to read
from shared runtime/build configuration instead of using a literal false, and
keep the existing WebSocket connection setup in app.js driven by that shared
flag so the opt-in flow works end to end.

Comment thread server.js
Comment on lines +26 to +29
const WEBSOCKET_ENABLED = process.env.ENABLE_WEBSOCKET === 'true';
let WebSocket = null;
let isWebSocketAvailable = false;
if (WEBSOCKET_ENABLED) {

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🎯 Functional Correctness | 🟡 Minor | ⚡ Quick win

Separate “disabled by config” from “ws unavailable”.

This gate reuses isWebSocketAvailable for both states, so POST /message now tells clients to install ws even when WebSockets were only disabled via ENABLE_WEBSOCKET. Return a config-disabled 503 body separately from the missing-dependency case.

Also applies to: 38-40

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@server.js` around lines 26 - 29, The WebSocket gating in server.js conflates
configuration-disabled and dependency-missing states via isWebSocketAvailable,
so split the logic around WEBSOCKET_ENABLED and the ws import in the startup
block and POST /message handler. Keep a separate flag or branch for “disabled by
config” versus “ws unavailable,” and return a distinct 503 response for each
case so clients only see the install-ws message when the dependency is actually
missing.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants