Claim a Sandbox
Reserve one computer from existing Cloud Fleet capacity with Python or TypeScript.
A claim reserves one computer from an existing Fleet pool. Python uses the Cua Sandbox SDK to expose that computer through the Sandbox APIs. TypeScript uses the Fleet SDK for hosted claim lifecycle and service routing; it is not a TypeScript Sandbox SDK.
The examples use the pool's server service to prove the claimed computer is
usable. Create a pool first with Create Fleet capacity,
or use a pool managed by your team.
Prerequisites#
- Permission to claim from the pool.
- The pool name and a distinct claim name for this task.
- A declared
serverservice on port8000.
export CUA_POOL_NAME="my-team-sandbox-pool"
export CUA_CLAIM_NAME="my-task"
export CUA_CLIENT_ID="<your-client-id>"
export CUA_CLIENT_SECRET="<your-client-secret>"Claim and use a computer#
Save this as claim_sandbox.py. The Python Sandbox SDK connects the claim to
the familiar shell and screenshot APIs exposed by computer-server.
# /// script
# requires-python = ">=3.11,<3.14"
# dependencies = [
# "cua-sandbox==0.7.0",
# ]
# ///
import asyncio
import os
from pathlib import Path
from cua_sandbox import Pool
async def main() -> None:
pool = await Pool.get(os.environ["CUA_POOL_NAME"])
async with pool.claim(
name=os.environ["CUA_CLAIM_NAME"],
service="server",
time_to_start=900,
) as sandbox:
print(f"Pool: {sandbox.pool_name}")
print(f"Claim: {sandbox.claim_name}")
result = await sandbox.shell.run("uname -a")
if not result.success:
raise RuntimeError(result.stderr)
print(result.stdout.strip())
Path("sandbox.png").write_bytes(await sandbox.screenshot())
asyncio.run(main())Run it:
uv run claim_sandbox.pyThe claim context reconnects to an existing named claim when one is present,
waits up to 900 seconds for server, and releases the claim on exit.
Result and lifecycle#
Both paths reserve one computer, wait for the server service, capture a
screenshot through computer-server, and release only the claim. The pool and
its warm capacity remain available and can continue consuming capacity. Copy
results out before release; a later claim is not guaranteed to receive the same
VM or files.
Claim names are scoped to the pool. Give concurrent tasks different names. A Python named claim that still exists is reconnected; the TypeScript example creates a claim and should use a fresh name after release.
Keep a Python claim between processes#
The Python Sandbox SDK can disconnect while leaving its claim held. Save the Sandbox reference before disconnecting:
import json
from pathlib import Path
sandbox = await pool.claim(name=CLAIM_NAME, service="server", time_to_start=900)
try:
Path("claim.json").write_text(json.dumps(sandbox.to_dict()))
finally:
await sandbox.disconnect()Reconnect with Sandbox.from_dict(reference). That context disconnects on
exit; call await sandbox.close() when the task is finished to release the
claim. A saved reference does not extend its expiry deadline.
If acquisition or cleanup is interrupted, retain the pool and claim names and follow Recover interrupted cleanup.