Run e2b code on Spaces
Swap the e2b dependency for cua-e2b: sandboxes become Spaces on your own machines. What maps, what refuses, and how to check it.
cua-e2b is a drop-in replacement for the e2b Python package. Install it in
place of e2b and code written for e2b 2.42, 2.56 or 2.58 keeps working; every
sandbox is a Space of kind vm (a Linux VM) placed on your machines.
uv pip uninstall e2b && uv pip install cua-e2bfrom e2b import AsyncSandbox, CommandExitException
sandbox = await AsyncSandbox.create(template="my-world", timeout=3600)
try:
result = await sandbox.commands.run("uname -a", user="root")
await sandbox.files.write("/tmp/in.tar", data, user="root")
finally:
await sandbox.kill()Do not want to change the dependency? cua run --compat e2b -- python your_script.py
runs the unmodified e2b SDK against a local gateway instead. The shim and the
gateway are held to the same recorded E2B behaviour.
What maps#
| e2b | Cua |
|---|---|
create(template=...) | A Cua checkpoint (the sandbox is forked from it, memory included) or an image. None or "base" is the canonical Linux image. |
| placement | CUA_E2B_ON (default auto: the least-loaded of your machines), CUA_E2B_KIND, CUA_E2B_CPUS, CUA_E2B_MEMORY_MB. |
timeout, set_timeout, lifecycle | A Space lifetime kept by the daemon: the Space is deleted (or suspended for on_timeout="pause") even after your process exits. |
commands, pty, git, files, watch_dir | cua-spacesd's process and file services; commands run as /bin/bash -l -c; other users through sudo -n. |
get_host(port) | A loopback host:port forwarded through cua-spacesd's tunnel to a Space on any of your machines. |
download_url, upload_url | Signed /files URLs minted by cua-spacesd (24 hours at most). |
pause, connect, fork, snapshots | Suspend and resume, copy-on-write forks of a running VM, pinned checkpoints. |
Template builder, Volume | Recipes run in a VM and saved as a snapshot; volumes are folders of Cua Volume. |
network with IP and CIDR rules, update_network | Rules enforced inside the Space. |
What refuses, and why#
The calls below raise e2b's own exception classes with a message that names the way out. None is a silent no-op.
iam=...,Secretoperations,networkrulesandegress_proxy: they belong to E2B's control plane and its TLS-intercepting proxy. Pass credentials withenvs=(cua run --env KEY) or keep them in Keyvault.- Hostnames in
allow_outanddeny_out: rules are by IP address and CIDR. - Template bases that are bare OCI images: Spaces boot Cua images.
get_hostis plain TCP: usehttp://. Code that hard-codeshttps://runs throughcua run --compat e2b, which serves TLS.
The complete list, with the test that proves each row, is generated into
libs/python/cua-e2b/COVERAGE.md.
How it is checked#
- Surface. Every public module, class, function, method, field and enum value of e2b 2.42.0, 2.56.0 and 2.58.0 is recorded and compared with cua-e2b on every pull request; a weekly job compares the latest release.
- Behaviour. One conformance suite runs against the real e2b package and E2B, and against cua-e2b and real Linux Spaces. Results recorded from E2B are the goldens; cua-e2b must match them case by case.
- Cost. A perf guard fails when the shim adds more than 1.5 times its committed overhead to an e2b call.