Skip to main content
Watch an agent work in real time, to step in when automation stalls, or to treat a browser or desktop as a disposable remote workbench. The GUI reaches you over a local port from whichever box provides it.

Pages in this section


Quick Example

The code below: (1) starts a sandbox that ships with a desktop (ComputerBox, image lscr.io/linuxserver/webtop:ubuntu-xfce); (2) waits until the desktop is ready; (3) prints a local URL you can open directly in a browser, then keeps running until you press Enter. During that window you can operate the sandbox like a remote desktop in your browser.
After it runs, open http://localhost:3000 in a browser to view and operate the sandbox desktop. When you close the script (press Enter), the sandbox and every change inside it are destroyed.
Node users: ComputerBox is also available in the Node SDK (import { ComputerBox } from "@boxlite-ai/boxlite"), with camelCase method names (waitUntilReady / screenshot, etc.). The GUI port exposure logic is identical.

Three paths for a human to reach the GUI

Choose by what you need to view or operate. Each path corresponds to one GUI-bearing, purpose-built box:
All three inherit from SimpleBox, so you can also run commands with await box.exec(...) and transfer files with copy_in / copy_out. The GUI is the extra “human view” they expose.

Path A: full desktop (ComputerBox)

The most direct “remote desktop” approach. See the Quick Example above. Key points:
  • The GUI ports are fixed and controllable on the host side (constructor arguments gui_http_port / gui_https_port, defaults 3000 / 3001).
  • HTTPS uses a self-signed certificate, so the browser shows a security warning; click “Advanced -> Proceed” to continue.
  • Default resolution is 1024x768 (controlled by the DISPLAY_SIZEW / DISPLAY_SIZEH environment variables, which are injected for you).

Path B: watch an AI agent run (SkillBox)

SkillBox runs an AI CLI such as Claude Code inside the sandbox and ships with a noVNC desktop, so you can watch in real time while a task completes. Its GUI ports are randomly assigned by default (constructor arguments default to 0); read the assigned values from the instance attributes gui_http_port / gui_https_port:

Path C: manually take over the in-sandbox browser (BrowserBox)

BrowserBox runs a Playwright browser inside the sandbox. What it exposes is a debugging endpoint (CDP / Playwright Server endpoint), not a web desktop. You can:
  • Get the CDP address with await box.endpoint() and paste it into Chrome’s chrome://inspect to inspect pages and tune selectors — full walkthrough on Browser DevTools.
  • Get the Playwright Server address with await box.playwright_endpoint() and connect to it from a local script to observe while it runs.
For Playwright Server mode (which supports all browser types and is connected to with connect() from a local script), use await browser.playwright_endpoint(timeout=60) instead, and do not also call endpoint() on the same instance. Both modes occupy in-sandbox port 3000, so they are mutually exclusive.

Parameters and Returns

BrowserBox configuration is not passed as constructor keyword arguments but wrapped in BrowserBoxOptions: BrowserBox(BrowserBoxOptions(browser="firefox")). Writing BrowserBox(browser=...) directly raises TypeError.
BrowserBoxOptions fields (all optional; a dataclass):
playwright_endpoint() and endpoint() are mutually exclusive modes; a single BrowserBox instance uses only one of them.

Troubleshooting

The browser warns “Your connection is not private” when opening the HTTPS desktop

The HTTPS desktop on ComputerBox / SkillBox uses a self-signed certificate; this is expected. Click “Advanced -> Proceed to localhost”, or switch to the HTTP port (gui_http_port, default 3000).

http://localhost:3000 will not open / connection refused

  • Confirm the script is still running. Once the async with block exits, the sandbox is destroyed and the port closes with it. The Quick Example suspends the process with input(...) for exactly this reason.
  • Confirm await wait_until_ready() has returned; the desktop service takes seconds to tens of seconds to start.
  • The port is taken by another local program: change gui_http_port, for example ComputerBox(gui_http_port=8080).
  • SkillBox ports are randomly assigned, so do not hardcode 3000; read the real value from box.gui_http_port.

SkillBox raises ValueError on startup

The Claude OAuth token is missing. Set the environment variable CLAUDE_CODE_OAUTH_TOKEN, or pass oauth_token="<YOUR_CLAUDE_CODE_OAUTH_TOKEN>" to the constructor (replace with your real token).

BrowserBox errors when calling endpoint() under webkit

CDP direct-connect mode does not support webkit. For webkit, use playwright_endpoint() (Playwright Server mode, which supports all browsers) instead.

The sandbox will not start (no hardware virtualization)

This is an environment constraint:
  • Hardware virtualization is required. Linux needs KVM (/dev/kvm readable/writable, user in the kvm group); macOS arm64 uses Apple’s Hypervisor.framework (no /dev/kvm needed); Windows uses WSL2 + KVM.
  • The first image pull depends on the network; on failure it raises a standard RuntimeError (you can try/except and retry), not a BoxliteError subclass.
  • macOS Intel: not supported.

The third volume element is mistakenly written as a string

If you mount a host directory for the desktop as volumes=[("/host", "/box", "ro")], you get:
In the SDK the third volume element is a bool read_only (True = read-only / False = read-write), not the string "ro" / "rw". The correct form is volumes=[("/host/path", "/box/path", True)], or a 2-tuple ("/host/path", "/box/path") (read-write by default). (Note: only the CLI’s -v syntax uses the ro / rw strings; this differs from the SDK, so do not conflate them.)
  • Agent Tools: let an AI agent (not a human) operate inside the sandbox.
  • Manage Sandbox: lifecycle, runtime methods, the context-manager model.