feat(ide): add vscode-web (serve-web) and code-server browser IDEs#769
Conversation
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Add experimental vscode-web and code-server IDEs to the desktop app, visible by default, mirroring how the Bob IDE was integrated. Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
|
Warning Review limit reached
More reviews will be available in 8 minutes and 50 seconds. Learn how PR review limits work. Your organization has run out of usage credits. Purchase more credits in the billing tab to continue. ⌛ How to resolve this issue?After more reviews become available, a review can be triggered using the To avoid repeated limits, reduce automatic review volume by pausing incremental auto-reviews earlier, using label-based review opt-in, excluding WIP or generated PR titles, or requesting reviews manually when the PR is ready. If your team needs uninterrupted high-volume reviews, an organization admin can enable usage-based credits. 🚦 How do rate limits work?CodeRabbit enforces per-developer PR review limits for each organization. Most developers receive the normal plan review availability. For paid Pro and Pro+ PR reviews, CodeRabbit uses adaptive limits for sustained high-volume activity. When a developer's recent PR review activity reaches the 95th percentile or higher among CodeRabbit users, additional reviews become available more gradually as earlier reviews age out of the rolling window. Please see our Fair Usage Limits Policy for further information. ℹ️ Review info⚙️ Run configurationConfiguration used: Organization UI Review profile: CHILL Plan: Pro Run ID: ⛔ Files ignored due to path filters (1)
📒 Files selected for processing (4)
📝 WalkthroughWalkthroughThis PR adds VS Code Web and code-server support across IDE registration, runtime setup, container wiring, browser opening, desktop exposure, tests, and related documentation. ChangesBrowser IDE support
Estimated code review effort🎯 4 (Complex) | ⏱️ ~60 minutes Possibly related PRs
Suggested reviewers
🚥 Pre-merge checks | ✅ 4 | ❌ 1❌ Failed checks (1 warning)
✅ Passed checks (4 passed)
✨ Finishing Touches🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
The repeated "true" literal in the vscode-web and code-server Options tripped golangci-lint's goconst linter (4 occurrences per file). Reuse the existing config.BoolTrue/BoolFalse constants instead. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
There was a problem hiding this comment.
Pull request overview
Adds two new browser-based VS Code IDE backends (vscode-web via code serve-web and code-server) alongside the existing openvscode, wiring them through the config/registry, agent container setup (including async extension install), browser tunnel opener, desktop UI settings, and e2e coverage.
Changes:
- Introduce new IDE implementations:
pkg/ide/vscodeweb(VS Code Web) andpkg/ide/codeserver(code-server), including release URL logic + unit tests. - Register new IDEs end-to-end: config enums, IDE registry, browser opener/tunneling, agent container setup & async extension installers, and e2e IDE suite.
- Expose IDEs in the desktop UI as experimental toggles, add icon mapping, and include them in supported IDE types.
Reviewed changes
Copilot reviewed 20 out of 20 changed files in this pull request and generated 6 comments.
Show a summary per file
| File | Description |
|---|---|
| pkg/ide/vscodeweb/vscodeweb.go | New VS Code Web installer/runner and option definitions |
| pkg/ide/vscodeweb/vscodeweb_test.go | Unit tests for VS Code Web release URL selection |
| pkg/ide/codeserver/codeserver.go | New code-server installer/runner and option definitions |
| pkg/ide/codeserver/codeserver_test.go | Unit tests for code-server release URL selection |
| pkg/config/ide.go | Adds new IDE enum values (vscode-web, code-server) |
| pkg/ide/ideparse/parse.go | Registers new IDEs in the allowed IDE registry |
| pkg/ide/ideparse/parse_registry_test.go | Verifies new IDEs are registered and have options |
| pkg/ide/types.go | Marks new IDEs as reusing the SSH auth sock (browser tunnel behavior) |
| pkg/ide/opener/opener.go | Adds browser openers for vscode-web and code-server |
| cmd/agent/container/setup.go | Wires new IDEs into container setup + async extension installation |
| cmd/agent/container/vscodeweb_async.go | Adds async extension install command for VS Code Web |
| cmd/agent/container/codeserver_async.go | Adds async extension install command for code-server |
| cmd/agent/container/container.go | Registers the new async subcommands |
| e2e/tests/ide/ide.go | Adds e2e coverage invoking the new IDEs |
| desktop/src/views/Settings/Settings.tsx | Adds experimental toggles for the two new IDEs |
| desktop/src/useIDEs.ts | Filters new IDEs based on experimental settings flags |
| desktop/src/types.ts | Adds new IDE strings to SUPPORTED_IDES |
| desktop/src/gen/Settings.ts | Extends generated Settings type with new experimental flags |
| desktop/src/contexts/SettingsContext/SettingsContext.tsx | Adds defaults for new experimental settings flags |
| desktop/src/components/IDEIcon/IDEIcon.tsx | Adds icon mapping for the new IDE IDs |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
There was a problem hiding this comment.
Actionable comments posted: 8
🧹 Nitpick comments (1)
pkg/ide/ideparse/parse_registry_test.go (1)
5-14: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick winAssert a concrete options contract here.
This only proves the entries exist. A miswired or empty
ide.Optionsmap would still pass, so the test would miss the regression this PR is trying to guard against. Please also assert at least one stable option key per IDE (for example the version option) so the registry wiring is actually verified.🤖 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 `@pkg/ide/ideparse/parse_registry_test.go` around lines 5 - 14, The TestNewBrowserIDEsRegistered check only verifies that GetIDEOptions returns non-nil values for “vscode-web” and “code-server”, so it can miss a miswired or empty ide.Options map. Update this test to assert a concrete stable option key for each IDE, using GetIDEOptions and the returned options map, so the registry wiring is actually validated rather than just existence.
🤖 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 `@cmd/agent/container/setup.go`:
- Around line 681-688: The browser IDE startup paths in setupOpenVSCode,
vscode-web, and code-server are reusing the same workspace port, which causes
conflicts when switching IDEs on an existing workspace. Update the startup flow
to either tear down the previously started browser daemon before launching a
different IDE or assign each IDE its own distinct port, and make the
StartBackgroundOnce keys in the affected setup functions reflect the chosen
reuse/teardown behavior so the opener always targets the requested IDE.
In `@desktop/src/views/Settings/Settings.tsx`:
- Around line 539-557: The experimental toggle rows in Settings.tsx use
standalone Switch and FormLabel pairs without explicit association, so update
the block around the settings toggles to bind each label to its control using
FormControl or matching id/htmlFor props. Apply the same pattern consistently
across the experimental switch rows, including the ones for
experimental_vscodeWeb and experimental_codeServer, so each label is correctly
linked to its Switch.
In `@pkg/ide/codeserver/codeserver.go`:
- Around line 172-183: The command construction in codeserver.go is
interpolating configurable values into a shell string, which is unsafe and can
break quoting; update the code around runCommand and exec.Command in the
codeServer launch path to avoid shell interpolation for host, port, and
extension-related values. Build argv directly for the Code Server invocation
where possible, and for the o.userName branch replace the raw su -c string path
with a safe user-switch approach or properly escaped shell-quoting helper. Apply
the same fix to the other similar command-building block referenced by the
review, keeping the fix localized to the command assembly logic.
- Around line 3-17: The download path in codeserver handling currently uses
devpodhttp.GetHTTPClient(), which skips TLS verification before extracting and
starting a tarball. Update the codeserver download/extract flow to use a
TLS-verifying client or download helper instead, and make sure the request path
rejects any non-2xx HTTP response before passing data to extract. Keep the fix
localized around the codeserver download logic and the extraction/startup flow
so the insecure client is no longer used there.
- Around line 117-120: The Install flow in codeserver.go returns immediately
when bin/code-server already exists, which skips installSettings() and prevents
updated workspace/user settings from being applied. Update the logic in the
Install function so the existing-install check only skips the binary
installation work, but still calls installSettings() before returning; keep the
change localized around the os.Stat check and the installSettings helper.
In `@pkg/ide/vscodeweb/vscodeweb.go`:
- Around line 171-183: The command construction in vscodeweb.go is vulnerable
because runCommand is assembled into sh -c / su -c strings using configurable
values like host, port, and extension IDs, so a single quote can break quoting
and inject shell syntax. Refactor the command path in the vscodeweb launcher
logic to build argv directly instead of interpolating shell strings, using
exec.Command with explicit arguments wherever possible. For the user-switch
case, replace the raw su -c string flow with a safe user-switch helper or a
proper shell-quoting helper, and apply the same fix to the related
extension-install command path as well. Use the existing runCommand/args
construction and exec.Command call sites as the main points to update.
- Around line 3-17: The executable download path in vscodeweb.go currently uses
devpodhttp.GetHTTPClient(), which bypasses TLS verification for a tarball that
is later extracted and executed; switch the download flow in the vscodeweb
setup/download helper to a TLS-verifying client or helper, and make sure the
response is checked for a successful 2xx status before calling extract logic.
Update the code around the vscodeweb installer/download routine and the extract
path so only verified, successful downloads are written and unpacked.
- Around line 117-120: The early return in vscodeweb.go inside the install flow
skips applying settings when the code binary already exists. Update the install
logic so the existing-install check still proceeds to installSettings() rather
than returning immediately, and keep the behavior localized around the existing
install path in the VSCodeWeb installer routine so workspace/user settings are
always applied.
---
Nitpick comments:
In `@pkg/ide/ideparse/parse_registry_test.go`:
- Around line 5-14: The TestNewBrowserIDEsRegistered check only verifies that
GetIDEOptions returns non-nil values for “vscode-web” and “code-server”, so it
can miss a miswired or empty ide.Options map. Update this test to assert a
concrete stable option key for each IDE, using GetIDEOptions and the returned
options map, so the registry wiring is actually validated rather than just
existence.
🪄 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: 5167f174-3f15-4b56-95ee-d8aa21fd816b
⛔ Files ignored due to path filters (1)
desktop/src/gen/Settings.tsis excluded by!**/gen/**
📒 Files selected for processing (19)
cmd/agent/container/codeserver_async.gocmd/agent/container/container.gocmd/agent/container/setup.gocmd/agent/container/vscodeweb_async.godesktop/src/components/IDEIcon/IDEIcon.tsxdesktop/src/contexts/SettingsContext/SettingsContext.tsxdesktop/src/types.tsdesktop/src/useIDEs.tsdesktop/src/views/Settings/Settings.tsxe2e/tests/ide/ide.gopkg/config/ide.gopkg/ide/codeserver/codeserver.gopkg/ide/codeserver/codeserver_test.gopkg/ide/ideparse/parse.gopkg/ide/ideparse/parse_registry_test.gopkg/ide/opener/opener.gopkg/ide/types.gopkg/ide/vscodeweb/vscodeweb.gopkg/ide/vscodeweb/vscodeweb_test.go
…n input Addresses Copilot review feedback on the new vscode-web and code-server IDEs: - Bind both IDEs to 127.0.0.1 instead of 0.0.0.0. DevPod's tunnel always dials localhost inside the container (pkg/tunnel/services.go), so loopback is sufficient and avoids exposing the servers on other container interfaces — important for code-server, which runs with --auth none. - Constrain the vscode-web VERSION option to the valid build channels (stable, insider) via an Enum so invalid values can't reach the download URL and the option is self-describing in the UI. - Trim an optional leading "v" from the code-server VERSION so "v4.126.0" doesn't produce a "vv4.126.0" release URL; covered by a new unit test. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Strengthen TestNewBrowserIDEsRegistered to assert each new browser IDE exposes a non-empty options map containing the stable VERSION option, rather than only checking the registry entry is non-nil. A miswired or empty ide.Options map now fails the test instead of silently passing. Addresses a CodeRabbit nitpick on the registry test. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Declutters the IDE picker now that there are three browser-based VS Code variants (openvscode, vscode-web, code-server): - Add an IDEGroupBrowser group and move all three browser IDEs into it, so the desktop picker renders a single "Browser" submenu instead of three flat top-level entries. The desktop "VS Code" stays in Primary. - Give vscode-web and code-server their own bundled desktop icons (vscodeweb.svg, codeserver.svg) instead of all three sharing openvscode's browser icon, so they're visually distinguishable. The registry Icon URLs stay on the existing hosted vscodebrowser.svg: the desktop app renders via the bundled IDE_ICONS map, and the website assets host (devpod.sh/assets) isn't ours to publish new SVGs to. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Replace the placeholder code-server icon with Coder's official logo from coder/code-server (src/browser/media/favicon.svg). Since the mark is monochrome, ship a light (near-black) and a dark (white) variant wired through the IDEIcon `<name>_dark` mechanism so it stays legible in both desktop color modes. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
- Rename the openvscode IDE's display name "VS Code Browser" -> "OpenVSCode Server" to match its upstream project (gitpod-io/openvscode-server). - Move VS Code Web onto the browser icon OpenVSCode Server previously used (vscodebrowser.svg), and give OpenVSCode Server its own official logo so the three browser IDEs stay visually distinct. Drop the now-unused vscodeweb.svg. - Add padding around the IDE icon in the create-workspace Default IDE grid so the icons aren't edge-to-edge. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
638e3ec to
d81ab1c
Compare
These spec/plan files are local development artifacts and were committed by mistake; keep them out of the PR.
| // Access is via DevPod's tunnel, which dials localhost inside the | ||
| // container; bind to loopback so the auth-less server isn't exposed | ||
| // on other container interfaces. | ||
| o.host = "127.0.0.1" |
There was a problem hiding this comment.
I wonder if this will regress with cloud providers.
| } | ||
|
|
||
| // code-server reads user settings from <user-data-dir>/User/settings.json. | ||
| settingsDir := filepath.Join(location, "data", "User") |
Summary
Adds two actively-maintained browser VS Code IDEs alongside the existing
openvscode, which downloads from the unmaintainedgitpod-io/openvscode-server(pinned tov1.84.2):--ide=vscode-webcode serve-web— always the latest VS Code, full Microsoft Marketplace. The small CLI is downloaded; the server bits are fetched at runtime on first connect.code-servercode-server— a self-contained tarball (no runtime download), Open VSX marketplace.openvscodeis left untouched, so existing--ide=openvscodeconfigs keep working.Closes #764
Screenshots
Browser IDEs grouped under one
Browser ▸submenu (Workspace → Open → Start with) — OpenVSCode Server, VS Code Web, and code-server, each with its own icon:Default IDE picker in Create Workspace — the browser IDEs are selectable and the grid icons now have padding:
Design
pkg/ide/openvscode/(the established convention used byopenvscode,jupyter,rstudio):pkg/ide/vscodeweb/andpkg/ide/codeserver/.openvscodeis: config enum → IDE registry (ideparse) → agentinstallIDE+ async extension install → browser opener + SSH auth-sock reuse → desktop app.SUPPORTED_IDES,useIDEsfilter,gen/Settings.ts,SettingsContext, and a Settings toggle each).~/.vscode-web,~/.code-server) to avoid colliding with the regularvscodeserver, whose binary is itself namedcode-serverand lives in~/.vscode-server.code serve-webis started with--accept-server-license-terms(so the background process never blocks on a prompt) and--without-connection-token.Testing
go test ./pkg/ide/...passes (incl. newgetReleaseUrlunit tests); whole module builds;golangci-lintclean; desktopyarn types:check+yarn lint:ciclean. e2e cases added for both IDEs (run on CI/Linux via theidelabel).Validated both IDEs end-to-end against real Linux containers:
bin/code-server, serves HTTP 200; log confirmsUsing user-data-dir <dir>matching the configured path, and readsdata/User/settings.json.<dir>/code,code 1.126.0runs,serve-webstarts and serves the web UI accepting all configured flags; operates within<server-data-dir>/data/Machine/, confirming the Machine-settings path.Notes for reviewers
code serve-webfetches the VS Code server at runtime on first connect, so the container needs outbound network access.code-serverships self-contained.vscode-webuses the Microsoft Marketplace.code-serverversion default is pinned to4.126.0(overridable via theVERSIONIDE option);vscode-webuses thestablebuild channel.🤖 Generated with Claude Code
Summary by CodeRabbit