Skip to content

fix(browser-capture): stop silently elevating CA install/uninstall#67

Merged
ZYKJShadow merged 1 commit into
masterfrom
fix/cert-install-no-fallthrough
Apr 28, 2026
Merged

fix(browser-capture): stop silently elevating CA install/uninstall#67
ZYKJShadow merged 1 commit into
masterfrom
fix/cert-install-no-fallthrough

Conversation

@ZYKJShadow
Copy link
Copy Markdown
Owner

Summary

The Windows CA installer used to fall through from a user-store certutil call to a UAC-elevated machine-store call whenever the first attempt returned a non-zero exit code — including the case where the user just clicked "No" on Windows' standard root-trust dialog. Combined with a 2.5–6 s poll of proxyCaRefresh that could flip the install/uninstall toggle, users reported a surprise "asks to install, then asks to uninstall" sequence with multiple system prompts per click.

This PR removes the silent elevation, distinguishes "cert not in this store" from "command failed", throttles the polling, and adds a confirm dialog so a stale toggle state can never silently invoke the system trust prompt.

  • main-src/browser/browserCaInstaller.ts
    • install / uninstall now take an explicit scope: 'user' | 'machine'. They never auto-escalate.
    • macOS user-scope install uses the login keychain (no sudo); only machine scope goes through sudo-prompt.
    • Linux uninstall short-circuits when the cert file is absent.
    • Windows uninstall checks the relevant store first; if the cert isn't there, it returns successfully without spawning certutil and (for machine) without triggering UAC.
  • main-src/ipc/handlers/browserHandlers.ts
    • browserCapture:proxyCaInstall / proxyCaUninstall now accept { scope } (defaults to user).
  • src/AgentBrowserWindowSurface.tsx
    • The proxyCaRefresh poller now runs only while the proxy is actively running and at a 15 s cadence (was 2.5 s while running, 6 s while idle).
    • The install/uninstall button shows a window.confirm with localized copy before invoking the IPC.
  • src/i18n/messages.{en,zh-CN}.ts
    • New copy: browserCaptureCaInstallConfirm, browserCaptureCaInstallMachineConfirm, browserCaptureCaUninstallConfirm, browserCaptureCaInstallMachine.

Test plan

  • Windows: open the agent browser, start the capture proxy, click Install CA — confirm only one Windows root-trust prompt appears, no UAC.
  • Windows: with the CA installed in the user store, click Uninstall — verify it removes silently, no UAC.
  • Windows: with the CA NOT installed anywhere, click Uninstall — verify the call returns ok without spawning certutil and without UAC.
  • macOS: Install CA in user scope writes to the login keychain without a sudo prompt; Uninstall removes it.
  • Linux: Install/Uninstall still work via sudo-prompt; uninstall on a fresh system is a no-op.
  • Confirm the per-15 s proxyCaRefresh poll only runs while the proxy is up; closing the proxy stops the timer.
  • Cancel button on the confirm dialog cancels the operation cleanly (no IPC sent).

🤖 Generated with Claude Code

The Windows CA installer used to fall through from a user-store
certutil call to a UAC-elevated machine-store call whenever the first
attempt returned a non-zero exit code (including the user clicking
"No" on Windows' standard root-trust dialog). Combined with a 2.5-6s
poll of `proxyCaRefresh`, this produced the surprise "asks to install,
then asks to uninstall" experience users reported.

- Make install/uninstall scope-explicit (`user` | `machine`); never
  auto-escalate. Mac/Linux paths take the same scope arg so user-mode
  installs no longer require sudo.
- Distinguish "cert not in this store" from "command failed" so the
  uninstall path doesn't trigger UAC when there's nothing to remove.
- Throttle the proxy/CA status poll to 15s and only run while the proxy
  is actually running.
- Add a confirm dialog before triggering install/uninstall so a stale
  toggle state can't silently invoke the system trust prompt.

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
@ZYKJShadow ZYKJShadow merged commit 7d0e545 into master Apr 28, 2026
1 check passed
@ZYKJShadow ZYKJShadow deleted the fix/cert-install-no-fallthrough branch April 28, 2026 15:36
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.

1 participant